Si aún no has configurado el SDK de RUM para iOS, sigue las instrucciones de configuración en la aplicación o consulta la documentación de configuración de RUM para iOS.

Enriquecer las sesiones de usuario

El RUM para iOS rastrea automáticamente atributos como la actividad del usuario, pantallas, errores y solicitudes de red. Consulta la documentación de Recopilación de Datos de RUM para aprender sobre los eventos de RUM y los atributos predeterminados. Puedes enriquecer aún más la información de la sesión de usuario y obtener un control más fino sobre los atributos recopilados al rastrear eventos personalizados.

Visualizaciones personalizadas

Además de rastrear visualizaciones automáticamente, también puedes rastrear visualizaciones distintas específicas, como viewControllers cuando se vuelven visibles e interactivas. Detén el rastreo cuando la visualización ya no sea visible utilizando los siguientes métodos en RUMMonitor.shared():

  • .startView(viewController:)
  • .stopView(viewController:)

Por ejemplo:

import DatadogRUM

// in your `UIViewController`:
let rum = RUMMonitor.shared()

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    rum.startView(viewController: self)
}

override func viewDidDisappear(_ animated: Bool) {
  super.viewDidDisappear(animated)
  rum.stopView(viewController: self)
}
@import DatadogRUM;
// in your `UIViewController`:

DDRUMMonitor *rum = [DDRUMMonitor shared];

- (void)viewDidAppear:(BOOL)animated {
    [super viewDidAppear:animated];

    [rum startViewWithViewController:self name:nil attributes:nil];
}

- (void)viewDidDisappear:(BOOL)animated {
    [super viewDidDisappear:animated];

    [rum stopViewWithViewController:self attributes:nil];
}

Para más detalles y opciones disponibles, consulte RUMMonitorProtocol en GitHub.

Acciones personalizadas

Además de rastrear acciones automáticamente, también puedes rastrear acciones personalizadas específicas de los usuarios (toques, clics y desplazamientos) con la API de addAction(type:name:).

Para registrar manualmente acciones instantáneas de RUM como .tap en RUMMonitor.shared(), use .addAction(type:name:). Para acciones continuas de RUM como .scroll, use .startAction(type:name:) o .stopAction(type:).

Por ejemplo:

import DatadogRUM

// in your `UIViewController`:

let rum = RUMMonitor.shared()

@IBAction func didTapDownloadResourceButton(_ sender: UIButton) {
    rum.addAction(
        type: .tap,
        name: sender.currentTitle ?? ""
    )
}
- (IBAction)didTapDownloadResourceButton:(UIButton *)sender {
    NSString *name = sender.currentTitle ? sender.currentTitle : @"";
    [[DDRUMMonitor shared] addActionWithType:DDRUMActionTypeTap name:name attributes:@{}];
}

Nota: Al usar .startAction(type:name:) y .stopAction(type:), la acción type debe ser la misma. Esto es necesario para que el SDK de RUM de iOS coincida el inicio de una acción con su finalización.

Para más detalles y opciones disponibles, consulte RUMMonitorProtocol en GitHub.

Recursos personalizados

Además de rastrear recursos automáticamente, también puedes rastrear recursos personalizados específicos como solicitudes de red o API de proveedores de terceros. Usa los siguientes métodos en RUMMonitor.shared() para recopilar manualmente recursos de RUM:

  • .startResource(resourceKey:request:)
  • .stopResource(resourceKey:response:)
  • .stopResourceWithError(resourceKey:error:)
  • .stopResourceWithError(resourceKey:message:)

Por ejemplo:

import DatadogRUM

// in your network client:

let rum = RUMMonitor.shared()

rum.startResource(
    resourceKey: "resource-key",
    request: request
)

rum.stopResource(
    resourceKey: "resource-key",
    response: response
)
// in your network client:

[[DDRUMMonitor shared] startResourceWithResourceKey:@"resource-key"
                                            request:request
                                         attributes:@{}];

[[DDRUMMonitor shared] stopResourceWithResourceKey:@"resource-key"
                                          response:response
                                        attributes:@{}];

Nota: El String utilizado para resourceKey en ambas llamadas debe ser único para el recurso que está llamando. Esto es necesario para que el SDK de RUM de iOS coincida el inicio de un recurso con su finalización.

Para más detalles y opciones disponibles, consulte RUMMonitorProtocol en GitHub.

Errores personalizados

Para rastrear errores específicos, notifique a RUMMonitor.shared() cuando ocurra un error utilizando uno de los siguientes métodos:

  • .addError(message:)
  • .addError(error:)
let rum = RUMMonitor.shared()
rum.addError(message: "error message.")
[[DDRUMMonitor shared] addErrorWithMessage:@"error message." stack:nil source:DDRUMErrorSourceCustom attributes:@{}];

Para más detalles y opciones disponibles, consulte RUMMonitorProtocol en GitHub y la documentación de atributos de error.

Rastrear atributos globales personalizados

Además de los atributos RUM predeterminados capturados automáticamente por el SDK de RUM para iOS, puede optar por agregar información contextual adicional (como atributos personalizados) a sus eventos RUM para enriquecer su observabilidad dentro de Datadog.

Los atributos personalizados te permiten filtrar y agrupar información sobre el comportamiento del usuario observado (por ejemplo, el valor del carrito, el nivel del comerciante o la campaña publicitaria) junto con información a nivel de código (como servicios de backend, cronología de sesiones, registros de errores y salud de la red).

Los atributos personalizados están destinados a piezas pequeñas y específicas de información (por ejemplo, IDs, banderas o etiquetas cortas). Evite adjuntar objetos grandes como cargas útiles completas de respuestas HTTP. Esto puede aumentar significativamente el tamaño del evento e impactar el rendimiento.

Establecer un atributo global personalizado

Para establecer un atributo global personalizado, use RUMMonitor.shared().addAttribute(forKey:value:).

  • Para agregar un atributo, use RUMMonitor.shared().addAttribute(forKey: "<KEY>", value: "<VALUE>").
  • Para actualizar el valor, use RUMMonitor.shared().addAttribute(forKey: "<KEY>", value: "<UPDATED_VALUE>").
  • Para eliminar la clave, use RUMMonitor.shared().removeAttribute(forKey: "<KEY_TO_REMOVE>").

Para un mejor rendimiento en operaciones masivas (modificando múltiples atributos a la vez), use .addAttributes(_:) y .removeAttributes(forKeys:).

Nota: No puede crear facetas en atributos personalizados si utiliza espacios o caracteres especiales en los nombres de sus claves. Por ejemplo, use forKey: "store_id" en lugar de forKey: "Store ID".

Rastrear sesiones de usuario

Agregar información del usuario a sus sesiones de RUM facilita:

  • Seguir el recorrido de un usuario determinado
  • Saber qué usuarios son los más afectados por errores
  • Monitorear el rendimiento de sus usuarios más importantes
API de usuario en la interfaz de usuario de RUM
AtributoTipoDescripción
usr.idCadena(Requerido) Identificador único del usuario.
usr.nameCadena(Opcional) Nombre amigable del usuario, mostrado por defecto en la interfaz de usuario de RUM.
usr.emailCadena(Opcional) Correo electrónico del usuario, mostrado en la interfaz de usuario de RUM si el nombre de usuario no está presente.

Para identificar sesiones de usuario, use la Datadog.setUserInfo(id:name:email:) API.

Por ejemplo:

import DatadogCore

Datadog.setUserInfo(id: "1234", name: "John Doe", email: "john@doe.com")
[DDDatadog setUserInfoWithId:@"1234" name:@"John Doe" email:@"john@doe.com" extraInfo:@{}];

Rastrear eventos en segundo plano

Rastrear eventos en segundo plano puede llevar a sesiones adicionales, lo que puede afectar la facturación. Para preguntas, contacte al soporte de Datadog.

Puede rastrear eventos como fallos y solicitudes de red cuando su aplicación está en segundo plano (por ejemplo, no hay visualización activa disponible).

Para rastrear eventos en segundo plano, agregue el siguiente fragmento durante la inicialización en su configuración de Datadog:

import DatadogRUM

RUM.enable(
  with: RUM.Configuration(
    ...
    trackBackgroundEvents: true
  )
)

Parámetros de inicialización

Puede usar las siguientes propiedades en Datadog.Configuration al crear la configuración de Datadog para inicializar la biblioteca:

backgroundTasksEnabled
Esta bandera determina si los métodos UIApplication beginBackgroundTask(expirationHandler:) y endBackgroundTask: se utilizan para realizar cargas en segundo plano. Habilitar esta opción podría aumentar el tiempo que la aplicación opera en segundo plano en 30 segundos. Las tareas normalmente se detienen cuando no hay nada que subir o cuando se encuentra un obstáculo para la carga, como no tener conexión a internet o tener poca batería. Por defecto, esta opción está configurada en false.
batchProcessingLevel
El nivel de procesamiento por lotes define el número máximo de lotes procesados secuencialmente sin un retraso dentro de un ciclo de lectura/carga. El valor predeterminado es .medium.
batchSize
Establece el tamaño preferido de los datos agrupados que se suben a Datadog. Este valor impacta el tamaño y número de solicitudes realizadas por el SDK de RUM para iOS (lotes pequeños significan más solicitudes, pero cada solicitud se vuelve más pequeña en tamaño). Los valores disponibles incluyen: .small, .medium y .large.
bundle
El objeto de paquete que contiene el ejecutable actual.
clientToken
Ya sea el token del cliente de RUM (que soporta RUM, Logging y APM) o el token de cliente regular (que soporta Logging y APM).
encryption
Cifrado de datos a utilizar para la persistencia de datos en disco proporcionando un objeto que cumpla con el protocolo DataEncryption.
env
El nombre del entorno que se envía a Datadog. Esto puede ser utilizado para filtrar eventos por diferentes entornos (como staging o production).
proxyConfiguration
Un atributo de configuración de proxy que puede ser utilizado para habilitar un proxy personalizado para subir datos rastreados a la entrada de Datadog.
serverDateProvider
Una interfaz de sincronización NTP personalizada. Por defecto, el SDK de Datadog se sincroniza con grupos NTP dedicados proporcionados por el Proyecto NTP Pool. Usar diferentes grupos o establecer una implementación de no operación ServerDateProvider resulta en una desincronización de la instancia del SDK y los servidores de Datadog. Esto puede llevar a cambios significativos en el tiempo en sesiones de RUM o trazas distribuidas.
service
El nombre del servicio asociado con los datos enviados a Datadog. El valor predeterminado es el identificador del paquete de la aplicación.
site
El punto de conexión del servidor de Datadog al que se envían los datos. El valor predeterminado es .us1.
uploadFrequency
La frecuencia preferida para cargar datos a Datadog. Los valores disponibles incluyen: .frequent, .average y .rare.

Configuración de RUM

Puedes usar las siguientes propiedades en RUM.Configuration al habilitar RUM:

actionEventMapper
Establece la función de limpieza de datos para las acciones. Esto se puede usar para modificar o eliminar eventos de acción antes de que sean enviados a Datadog. Para más información, consulte Modificar o eliminar eventos de RUM.

appHangThreshold Establece el umbral para informar cuando una aplicación se cuelga. El valor mínimo permitido para esta opción es 0.1 segundos. Para deshabilitar el informe, establezca este valor en nil. Para más información, consulte Agregar informe de cuelgue de aplicación.

applicationID El identificador de la aplicación RUM.

customEndpoint Una URL de servidor personalizada para enviar datos RUM.

errorEventMapper La función de limpieza de datos para errores. Esto se puede usar para modificar o eliminar eventos de error antes de que se envíen a Datadog. Para más información, consulte Modificar o eliminar eventos RUM.

longTaskEventMapper La función de limpieza de datos para tareas largas. Esto se puede usar para modificar o eliminar eventos de tareas largas antes de que se envíen a Datadog. Para más información, consulte Modificar o eliminar eventos RUM.

longTaskThreshold El umbral para el seguimiento de tareas largas de RUM (en segundos). Por defecto, esto se envía a 0.1 segundos.

networkSettledResourcePredicate El predicado utilizado para clasificar los recursos “iniciales” para el cálculo del tiempo de vista de Tiempo-a-Red-Establecido (TNS).

nextViewActionPredicate El predicado utilizado para clasificar la acción “última” para el cálculo del tiempo de Interacción-a-Siguiente-Vista (INV).

onSessionStart (Opcional) El método que se llama cuando RUM inicia la sesión.

resourceEventMapper La función de limpieza de datos para los recursos. Esto se puede utilizar para modificar o eliminar eventos de recursos antes de que se envíen a Datadog. Para más información, consulte Modificar o eliminar eventos RUM.

sessionSampleRate La tasa de muestreo para las sesiones de RUM. El valor sessionSampleRate debe estar entre 0.0 y 100.0. Un valor de 0.0 significa que no se envían sesiones, mientras que 100.0 significa que se envían todas las sesiones a Datadog. El valor predeterminado es 100.0.

telemetrySampleRate La tasa de muestreo para la telemetría interna del SDK utilizada por Datadog. Esta tasa controla el número de solicitudes reportadas al sistema de trazado. Esto debe ser un valor entre 0 y 100. Por defecto, esto se establece en 20.

trackAnonymousUser Cuando está habilitado, el SDK genera un ID de usuario anónimo único y no personal que se mantiene a través de los lanzamientos de la aplicación. Este ID se adjuntará a cada sesión de RUM, lo que le permitirá vincular sesiones que provienen del mismo usuario/dispositivo sin recopilar datos personales. Por defecto, esto está configurado en true.

trackBackgroundEvents Determina si se rastrean eventos de RUM cuando no hay una vista activa. Por defecto, esto está configurado en false.

trackFrustrations Determina si se habilita el rastreo automático de frustraciones del usuario. Por defecto, esto está configurado en true.

trackMemoryWarnings Determina si se habilita el rastreo automático de advertencias de memoria. Por defecto, esto está configurado en true.

trackWatchdogTerminations Determina si el SDK debe rastrear las terminaciones de la aplicación realizadas por Watchdog. La configuración predeterminada es false.

uiKitActionsPredicate Habilita el rastreo de interacciones del usuario (toques) como acciones de RUM. Puede usar la implementación predeterminada de predicate configurando el DefaultUIKitRUMActionsPredicate o implementar su propia UIKitRUMActionsPredicate personalizada para su aplicación.

uiKitViewsPredicate Habilita el rastreo de UIViewControllers como vistas de RUM. Puede utilizar la implementación predeterminada de predicate configurando el DefaultUIKitRUMViewsPredicate o implementar su propia UIKitRUMViewsPredicate personalizada para su aplicación.

urlSessionTracking
Habilita el rastreo de URLSession tareas (solicitudes de red) como recursos de RUM. El parámetro firstPartyHostsTracing define los hosts que se clasifican como recursos first-party (si RUM está habilitado) y tienen información de seguimiento inyectada (si la función de seguimiento está habilitada). El parámetro resourceAttributesProvider define un cierre para proporcionar atributos personalizados para los recursos interceptados que se llama para cada recurso recopilado por el SDK de RUM para iOS. Este cierre se llama con información de la tarea y puede devolver atributos de recurso personalizados o nil si no se deben adjuntar atributos.
viewEventMapper
La devolución de llamada de limpieza de datos para vistas. Esto se puede utilizar para modificar eventos de vista antes de que se envíen a Datadog. Para más información, consulte Modificar o eliminar eventos RUM.
vitalsUpdateFrequency
La frecuencia preferida para recopilar datos vitales móviles. Los valores disponibles incluyen: .frequent (cada 100 ms), .average (cada 500 ms), .rare (cada 1 s) y .never (que desactiva el monitoreo de vitales).

Seguimiento automático de vistas

Puede realizar un seguimiento automático de vistas con UIKit y SwiftUI.

UIKit

Para realizar un seguimiento automático de vistas (UIViewControllers), utilice la opción uiKitViewsPredicate al habilitar RUM. Por defecto, las vistas se nombran con el nombre de la clase del controlador de vista. Para personalizarlo, proporcione su propia implementación de predicate que cumpla con el protocolo UIKitRUMViewsPredicate:

public protocol UIKitRUMViewsPredicate {
    func rumView(for viewController: UIViewController) -> RUMView?
}
@objc
public protocol DDUIKitRUMViewsPredicate: AnyObject {
    func rumView(for viewController: UIViewController) -> DDRUMView?
}

Dentro de la implementación rumView(for:), su aplicación debe decidir si una instancia UIViewController dada debe iniciar una visualización RUM (devolver un valor) o no (devolver nil). El valor RUMView devuelto debe especificar el name y puede proporcionar información adicional attributes para la visualización RUM creada.

Por ejemplo, puede configurar el predicado para usar una verificación de tipo explícita para cada controlador de vista en su aplicación:

class YourCustomPredicate: UIKitRUMViewsPredicate {

    func rumView(for viewController: UIViewController) -> RUMView? {
        switch viewController {
        case is HomeViewController:     return .init(name: "Home")
        case is DetailsViewController:  return .init(name: "Details")
        default:                        return nil
        }
    }
}
@interface YourCustomPredicate : NSObject<DDUIKitRUMViewsPredicate>

@end

@implementation YourCustomPredicate

- (DDRUMView * _Nullable)rumViewFor:(UIViewController * _Nonnull)viewController {
    if ([viewController isKindOfClass:[HomeViewController class]]) {
        return [[DDRUMView alloc] initWithName:@"Home" attributes:@{}];
    }

    if ([viewController isKindOfClass:[DetailsViewController class]]) {
        return [[DDRUMView alloc] initWithName:@"Details" attributes:@{}];
    }

    return nil;
}

@end

Incluso, puede idear una solución más dinámica dependiendo de la arquitectura de su aplicación.

Por ejemplo, si sus controladores de vista utilizan accessibilityLabel de manera consistente, puede nombrar las vistas por el valor de la etiqueta de accesibilidad:

class YourCustomPredicate: UIKitRUMViewsPredicate {

    func rumView(for viewController: UIViewController) -> RUMView? {
        guard let accessibilityLabel = viewController.accessibilityLabel else {
            return nil
        }

        return RUMView(name: accessibilityLabel)
    }
}
@interface YourCustomPredicate : NSObject<DDUIKitRUMViewsPredicate>

@end

@implementation YourCustomPredicate

- (DDRUMView * _Nullable)rumViewFor:(UIViewController * _Nonnull)viewController {
    if (viewController.accessibilityLabel) {
        return [[DDRUMView alloc] initWithName:viewController.accessibilityLabel attributes:@{}];
    }

    return nil;
}

@end

Nota: El SDK de RUM para iOS llama a rumView(for:) muchas veces mientras su aplicación está en ejecución. Datadog recomienda mantener su implementación rápida y de un solo hilo.

SwiftUI

Para rastrear automáticamente vistas con SwiftUI, utilice la opción swiftUIViewsPredicate al habilitar RUM.

El mecanismo para extraer un nombre de vista de SwiftUI se basa en la reflexión. Como resultado, los nombres de las vistas pueden no ser siempre significativos. Si no se puede extraer un nombre significativo, se utiliza un nombre genérico como AutoTracked_HostingController_Fallback o AutoTracked_NavigationStackController_Fallback.

Puede usar el predicado predeterminado (DefaultSwiftUIRUMViewsPredicate) o proporcionar su propia implementación del protocolo SwiftUIRUMViewsPredicate para personalizar o filtrar los nombres de las vistas.

public protocol SwiftUIRUMViewsPredicate {
    func rumView(for extractedViewName: String) -> RUMView?
}

// Example: Custom predicate to ignore fallback names and rename views
class CustomSwiftUIPredicate: SwiftUIRUMViewsPredicate {
    func rumView(for extractedViewName: String) -> RUMView? {
        if extractedViewName == "AutoTracked_HostingController_Fallback" ||
           extractedViewName == "AutoTracked_NavigationStackController_Fallback" {
            return nil // Ignore fallback names
        }
        if extractedViewName == "MySpecialView" {
            return RUMView(name: "Special")
        }
        return RUMView(name: extractedViewName)
    }
}
@protocol DDSwiftUIRUMViewsPredicate <NSObject>
- (DDRUMView * _Nullable)rumViewFor:(NSString * _Nonnull)extractedViewName;
@end

@interface CustomSwiftUIPredicate : NSObject <DDSwiftUIRUMViewsPredicate>
@end

@implementation CustomSwiftUIPredicate
- (DDRUMView * _Nullable)rumViewFor:(NSString * _Nonnull)extractedViewName {
    if ([extractedViewName isEqualToString:@"AutoTracked_HostingController_Fallback"] ||
        [extractedViewName isEqualToString:@"AutoTracked_NavigationStackController_Fallback"]) {
        return nil; // Ignore fallback names
    }
    if ([extractedViewName isEqualToString:@"MySpecialView"]) {
        return [[DDRUMView alloc] initWithName:@"Special" attributes:@{}];
    }
    return [[DDRUMView alloc] initWithName:extractedViewName attributes:@{}];
}
@end

Notas:

  • Datadog recomienda habilitar el rastreo de vistas de UIKit también, incluso si su aplicación está construida completamente con SwiftUI.

  • Las barras de pestañas no se rastrean automáticamente. Utilice rastreo manual para cada vista de pestaña para asegurarse de que se rastreen.

  • Si utiliza tanto el rastreo automático como el manual, puede ver eventos duplicados. Para evitar esto, confía en un único método de instrumentación o utiliza un predicado personalizado para filtrar duplicados.

Rastrear automáticamente las acciones del usuario

UIKit

Para rastrear automáticamente las acciones de toque del usuario con UIKit, configure la opción uiKitActionsPredicate al habilitar RUM.

SwiftUI

Para rastrear automáticamente las acciones de toque del usuario en SwiftUI, habilite la opción swiftUIActionsPredicate al habilitar RUM.

Notas:

  • Datadog recomienda habilitar el rastreo de acciones de UIKit incluso para aplicaciones puras de SwiftUI, ya que muchos componentes interactivos son UIKit en su núcleo.
  • En tvOS, solo se rastrean las interacciones de presión en el control remoto. Solo se necesita un predicado de UIKit para esto. Si tiene una aplicación pura de SwiftUI pero desea rastrear las presiones del control remoto en tvOS, también debe habilitar la instrumentación de UIKit.
  • La implementación difiere entre iOS 18+ e iOS 17 y anteriores:
    • iOS 18 y superiores: La mayoría de las interacciones se rastrean de manera confiable con los nombres de componentes correctos (por ejemplo, SwiftUI_Button, SwiftUI_NavigationLink).
    • iOS 17 y anteriores: El SDK no puede distinguir entre componentes interactivos y no interactivos (por ejemplo, Botón vs. Etiqueta). Por esa razón, las acciones se informan como SwiftUI_Unidentified_Element.
  • Si utiliza tanto el rastreo automático como el manual, puede ver eventos duplicados. Esta es una limitación conocida. Para evitar esto, utilice solo un tipo de instrumentación: automática o manual.
  • Puede usar el predicado predeterminado, DefaultSwiftUIRUMActionsPredicate, o proporcionar el suyo propio para filtrar o renombrar acciones. También puede deshabilitar la detección heredada (iOS 17 y anteriores) si solo desea un rastreo confiable en iOS 18+:
// Use the default predicate by disabling iOS 17 and below detection
let predicate = DefaultSwiftUIRUMActionsPredicate(isLegacyDetectionEnabled: false)

// Use your own predicate
class CustomSwiftUIActionsPredicate: SwiftUIRUMActionsPredicate {
    func rumAction(for componentName: String) -> RUMAction? {
        // Custom logic to filter or rename actions
        return RUMAction(name: componentName)
    }
}
// Use the default predicate by disabling iOS 17 and below detection
DDDefaultSwiftUIRUMActionsPredicate *swiftUIActionsPredicate = [[DDDefaultSwiftUIRUMActionsPredicate alloc] initWithIsLegacyDetectionEnabled:NO];

// Use your own predicate
@protocol DDSwiftUIRUMActionsPredicate <NSObject>
- (DDRUMAction * _Nullable)rumActionFor:(NSString * _Nonnull)componentName;
@end

@interface CustomSwiftUIActionsPredicate : NSObject <DDSwiftUIRUMActionsPredicate>
@end

@implementation CustomSwiftUIActionsPredicate
- (DDRUMAction * _Nullable)rumActionFor:(NSString * _Nonnull)componentName {
    // Custom logic to filter or rename actions
    return [[DDRUMAction alloc] initWithName:componentName attributes:@{}];
}
@end

Informe de acciones por versión de iOS

La tabla a continuación muestra cómo iOS 17 e iOS 18 informan diferentes interacciones del usuario.

ComponenteiOS 18 nombre reportadoiOS 17 nombre reportado
BotónSwiftUI_BotónSwiftUI_Elemento_No_Identificado
NavigationLinkNavigationLinkSwiftUI_Elemento_No_Identificado
MenúSwiftUI_Menú (y sus elementos como _UIContextMenuCell)SwiftUI_Menú (y sus elementos como _UIContextMenuCell)
EnlaceSwiftUI_BotónSwiftUI_Elemento_No_Identificado

Rastrear automáticamente las solicitudes de red

Las solicitudes de red se rastrean automáticamente después de habilitar RUM con la urlSessionTracking configuración.

(Opcional) Habilitar desglose de tiempo detallado

Para obtener un desglose de tiempo detallado (resolución DNS, apretón de manos SSL, tiempo hasta el primer byte, tiempo de conexión y duración de la descarga), habilite URLSessionInstrumentation para su tipo de delegado:

URLSessionInstrumentation.enableDurationBreakdown(
    with: .init(
        delegateClass: <YourSessionDelegate>.self
    )
)

let session = URLSession(
    configuration: .default,
    delegate: <YourSessionDelegate>(),
    delegateQueue: nil
)
DDURLSessionInstrumentationConfiguration *config = [[DDURLSessionInstrumentationConfiguration alloc] initWithDelegateClass:[<YourSessionDelegate> class]];
[DDURLSessionInstrumentation enableWithConfiguration:config];

NSURLSession *session = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]
                                                      delegate:[[<YourSessionDelegate> alloc] init]
                                                 delegateQueue:nil];

Notas:

  • Sin URLSessionInstrumentation, las solicitudes de red aún se rastrean. Habilitarlo proporciona un desglose de tiempo detallado para el análisis de rendimiento.
  • Los datos de respuesta están disponibles en el resourceAttributesProvider callback (establecido en RUM.Configuration.URLSessionTracking) para tareas con controladores de finalización en modo automático, y para todas las tareas después de habilitar URLSessionInstrumentation.
  • Para filtrar solicitudes específicas de ser rastreadas, use el resourceEventMapper en RUM.Configuration (ver Modificar o eliminar eventos RUM).
Tenga en cuenta la retención de delegados. Si bien la instrumentación de Datadog no crea fugas de memoria directamente, depende de URLSession delegados. Según la documentación de Apple: "El objeto de sesión mantiene una referencia fuerte al delegado hasta que su aplicación sale o invalida explícitamente la sesión. Si no invalida la sesión llamando al método invalidateAndCancel() o finishTasksAndInvalidate(), su aplicación genera fugas de memoria hasta que sale. Para evitar fugas de memoria, asegúrese de invalidar cualquier instancia de URLSession que ya no necesite.

Si tiene más de un tipo de delegado en su aplicación que desea instrumentar, puede llamar a URLSessionInstrumentation.enable(with:) para cada tipo de delegado.

Además, puede configurar hosts de primera parte utilizando urlSessionTracking. Esto clasifica los recursos que coinciden con el dominio dado como “primera parte” en RUM y propaga la información de trazado a su backend (si tiene habilitado el trazado). Las trazas de red se muestrean con una tasa de muestreo ajustable. Se aplica un muestreo del 20% por defecto.

Por ejemplo, puede configurar example.com como el host de primera parte y habilitar tanto las características de RUM como de Tracing:


import DatadogRUM

RUM.enable(
  with: RUM.Configuration(
    applicationID: "<rum application id>",
    uiKitViewsPredicate: DefaultUIKitRUMViewsPredicate(),
    uiKitActionsPredicate: DefaultUIKitRUMActionsPredicate(),
    urlSessionTracking: RUM.Configuration.URLSessionTracking(
        firstPartyHostsTracing: .trace(hosts: ["example.com"], sampleRate: 20)
    )
  )
)

URLSessionInstrumentation.enable(
    with: .init(
        delegateClass: <YourSessionDelegate>.self
    )
)

let session = URLSession(
    configuration: .default,
    delegate: <YourSessionDelegate>(),
    delegateQueue: nil
)

Esto rastrea todas las solicitudes enviadas con el session instrumentado. Las solicitudes que coinciden con el dominio example.com se marcan como “primera parte” y la información de trazado se envía a su backend para conectar el recurso RUM con su traza.

@import DatadogRUM;

DDRUMConfiguration *configuration = [[DDRUMConfiguration alloc] initWithApplicationID:@"<rum application id>"];
DDRUMURLSessionTracking *urlSessionTracking = [DDRUMURLSessionTracking new];
[urlSessionTracking setFirstPartyHostsTracing:[DDRUMFirstPartyHostsTracing alloc] initWithHosts:@[@"example.com"] sampleRate:20];
[configuration setURLSessionTracking:urlSessionTracking];

[DDRUM enableWith:configuration];

Para agregar atributos personalizados a los recursos, utilice la opción URLSessionTracking.resourceAttributesProvider al habilitar el RUM. Al establecer el cierre del proveedor de atributos, puede devolver atributos adicionales que se adjuntarán al recurso rastreado.

Por ejemplo, puede querer agregar encabezados de solicitud y respuesta HTTP al recurso RUM:

RUM.enable(
  with: RUM.Configuration(
    ...
    urlSessionTracking: RUM.Configuration.URLSessionTracking(
        resourceAttributesProvider: { request, response, data, error in
            return [
                "request.headers" : redactedHeaders(from: request),
                "response.headers" : redactedHeaders(from: response)
            ]
        }
    )
  )
)

Si no desea rastrear solicitudes, puede deshabilitar URLSessionInstrumentation para el tipo de delegado:

URLSessionInstrumentation.disable(delegateClass: <YourSessionDelegate>.self)
[DDURLSessionInstrumentation disableWithDelegateClass:[<YourSessionDelegate> class]];

Instrumentación de Apollo

Instrumentar Apollo en su aplicación iOS proporciona visibilidad de RUM sobre errores y rendimiento de GraphQL. Debido a que las solicitudes de GraphQL se envían todas a un único punto de conexión y, a menudo, devuelven 200 OK incluso en errores, la instrumentación HTTP por defecto carece de contexto. Permite que RUM capture el nombre de la operación, el tipo de operación y las variables (y opcionalmente la carga útil). Esto proporciona un contexto más detallado para cada solicitud de red.

Esta integración es compatible con Apollo iOS 1.0+ y Apollo iOS 2.0+. Siga las instrucciones para la versión de Apollo iOS que tiene a continuación.

  1. Configura la monitorización de RUM con Datadog iOS RUM.

  2. Agregue lo siguiente al archivo de su aplicación Package.swift:

    dependencies: [
        // For Apollo iOS 1.0+
        .package(url: "https://github.com/DataDog/dd-sdk-ios-apollo-interceptor", .upToNextMajor(from: "1.0.0"))
    
        // For Apollo iOS 2.0+
        .package(url: "https://github.com/DataDog/dd-sdk-ios-apollo-interceptor", .upToNextMajor(from: "2.0.0"))
    ]
    

    Alternativamente, puede agregarlo usando Xcode:

    1. Vaya a ArchivoAgregar Dependencias de Paquete.
    2. Ingrese la URL del repositorio: https://github.com/DataDog/dd-sdk-ios-apollo-interceptor.
    3. Seleccione la versión del paquete que coincida con su versión principal de Apollo (elija 1.x.x para Apollo iOS 1.0+ o 2.x.x para Apollo iOS 2.0+).
  3. Configure la instrumentación de red según su versión de Apollo iOS:

    Configura la instrumentación de red para el URLSessionClient integrado de Apollo:

    import Apollo
    
    URLSessionInstrumentation.enable(with: .init(delegateClass: URLSessionClient.self))
    

    Agregue el interceptor de Datadog a la configuración de su cliente Apollo:

    import Apollo
    import DatadogApollo
    
    class CustomInterceptorProvider: DefaultInterceptorProvider {
        override func interceptors<Operation: GraphQLOperation>(for operation: Operation) -> [ApolloInterceptor] {
            var interceptors = super.interceptors(for: operation)
            interceptors.insert(DatadogApolloInterceptor(), at: 0)
            return interceptors
        }
    }
    

    Configure la instrumentación de red utilizando los DatadogApolloDelegate y DatadogApolloURLSession proporcionados:

    import Apollo
    import DatadogApollo
    import DatadogCore
    
    // Create the Datadog delegate
    let delegate = DatadogApolloDelegate()
    
    // Create the custom URLSession wrapper
    let customSession = DatadogApolloURLSession(
        configuration: .default,
        delegate: delegate
    )
    
    // Enable Datadog instrumentation for the delegate
    URLSessionInstrumentation.enable(
        with: .init(delegateClass: DatadogApolloDelegate.self)
    )
    
    // Configure Apollo Client with the custom session
    let networkTransport = RequestChainNetworkTransport(
        urlSession: customSession,
        interceptorProvider: NetworkInterceptorProvider(),
        store: store,
        endpointURL: url
    )
    

    Cree un proveedor de interceptores con el interceptor de Datadog:

    import Apollo
    import DatadogApollo
    
    struct NetworkInterceptorProvider: InterceptorProvider {
        func graphQLInterceptors<Operation>(for operation: Operation) -> [any GraphQLInterceptor] where Operation : GraphQLOperation {
            return [DatadogApolloInterceptor()] + DefaultInterceptorProvider.shared.graphQLInterceptors(for: operation)
        }
    }
    

    Esto permite que Datadog RUM extraiga automáticamente el tipo de operación, nombre, variables y cargas útiles (opcional) de las solicitudes para enriquecer los recursos RUM de solicitudes GraphQL.

    • La integración soporta versiones de Apollo iOS 1.0+ y 2.0+.
    • Las operaciones de tipo consulta y mutación son rastreadas, las operaciones de suscripción no lo son.
    • El envío de cargas útiles de GraphQL está deshabilitado por defecto. Para habilitarlo, establezca el indicador sendGraphQLPayloads en el constructor de DatadogApolloInterceptor de la siguiente manera:
    
    let datadogInterceptor = DatadogApolloInterceptor(sendGraphQLPayloads: true)
      

Rastrear errores automáticamente

Todos los registros de “error” y “crítico” enviados con Logger se informan automáticamente como errores RUM y se vinculan a la vista RUM actual:

import DatadogLogs

let logger = Logger.create()

logger.error("message")
logger.critical("message")
@import DatadogLogs;

DDLogger *logger = [DDLogger create];
[logger error:@"message"];
[logger critical:@"message"];

De manera similar, todos los tramos finalizados marcados como error se informan como errores RUM:

import DatadogTrace

let span = Tracer.shared().startSpan(operationName: "operation")
// ... capture the `error`
span.setError(error)
span.finish()
// ... capture the `error`
id<OTSpan> span = [[DDTracer shared] startSpan:@"operation"];
[span setError:error];
[span finish];

Modificar o eliminar eventos RUM

Para modificar atributos de un evento RUM antes de que se envíe a Datadog o para eliminar un evento por completo, utiliza la API de Event Mappers al configurar el SDK de RUM para iOS:

let configuration = RUM.Configuration(
    applicationID: "<rum application id>",
    viewEventMapper: { RUMViewEvent in
        return RUMViewEvent
    }
    resourceEventMapper: { RUMResourceEvent in
        return RUMResourceEvent
    }
    actionEventMapper: { RUMActionEvent in
        return RUMActionEvent
    }
    errorEventMapper: { RUMErrorEvent in
        return RUMErrorEvent
    }
    longTaskEventMapper: { RUMLongTaskEvent in
        return RUMLongTaskEvent
    }
)
DDRUMConfiguration *configuration = [[DDRUMConfiguration alloc] initWithApplicationID:@"<rum application id>"];

[configuration setViewEventMapper:^DDRUMViewEvent * _Nonnull(DDRUMViewEvent * _Nonnull RUMViewEvent) {
    return RUMViewEvent;
}];

[configuration setErrorEventMapper:^DDRUMErrorEvent * _Nullable(DDRUMErrorEvent * _Nonnull RUMErrorEvent) {
    return RUMErrorEvent;
}];

[configuration setResourceEventMapper:^DDRUMResourceEvent * _Nullable(DDRUMResourceEvent * _Nonnull RUMResourceEvent) {
    return RUMResourceEvent;
}];

[configuration setActionEventMapper:^DDRUMActionEvent * _Nullable(DDRUMActionEvent * _Nonnull RUMActionEvent) {
    return RUMActionEvent;
}];

[configuration setLongTaskEventMapper:^DDRUMLongTaskEvent * _Nullable(DDRUMLongTaskEvent * _Nonnull RUMLongTaskEvent) {
    return RUMLongTaskEvent;
}];

Cada mapeador es un cierre de Swift con una firma de (T) -> T?, donde T es un tipo de evento RUM concreto. Esto permite cambiar partes del evento antes de que se envíe.

Por ejemplo, para redactar información sensible en un url de un recurso RUM, implemente una función redacted(_:) -> String personalizada y utilícela en resourceEventMapper:

let configuration = RUM.Configuration(
    applicationID: "<rum application id>",
    resourceEventMapper: { RUMResourceEvent in
        var RUMResourceEvent = RUMResourceEvent
        RUMResourceEvent.resource.url = redacted(RUMResourceEvent.resource.url)
        return RUMResourceEvent
    }
)
DDRUMConfiguration *configuration = [[DDRUMConfiguration alloc] initWithApplicationID:@"<rum application id>"];

[configuration setResourceEventMapper:^DDRUMResourceEvent * _Nullable(DDRUMResourceEvent * _Nonnull RUMResourceEvent) {
    return RUMResourceEvent;
}];

Devolver nil desde el mapeador de error, recurso o acción elimina el evento por completo; el evento no se envía a Datadog. El valor devuelto por el mapeador de eventos de vista no debe ser nil (para eliminar vistas, personalice su implementación de UIKitRUMViewsPredicate; lea más en seguimiento automático de vistas).

Dependiendo del tipo de evento, solo algunas propiedades específicas pueden ser modificadas:

Tipo de EventoClave de AtributoDescripción
RUMActionEventRUMActionEvent.action.target?.nameNombre de la acción.
RUMActionEvent.view.urlURL de la vista vinculada a esta acción.
RUMErrorEventRUMErrorEvent.error.messageMensaje de error.
RUMErrorEvent.error.stackTraza de pila del error.
RUMErrorEvent.error.resource?.urlURL del recurso al que se refiere el error.
RUMErrorEvent.view.urlURL de la vista vinculada a este error.
RUMResourceEventRUMResourceEvent.resource.urlURL del recurso.
RUMResourceEvent.view.urlURL de la vista vinculada a este recurso.
RUMViewEventRUMViewEvent.view.nameNombre de la vista.
RUMViewEvent.view.urlURL de la vista.
RUMViewEvent.view.referrerURL que enlazó a la vista inicial de la página.

Recuperar el ID de sesión RUM

Recuperar el ID de sesión RUM puede ser útil para la solución de problemas. Por ejemplo, puede adjuntar el ID de sesión a solicitudes de soporte, correos electrónicos o informes de errores para que su equipo de soporte pueda encontrar más tarde la sesión del usuario en Datadog.

Puede acceder al ID de sesión RUM en tiempo de ejecución sin esperar el evento sessionStarted:

RumMonitor.shared().currentSessionID(completion: { sessionId in
  currentSessionId = sessionId
})

Establecer consentimiento de seguimiento (cumplimiento del GDPR)

Para cumplir con la regulación del GDPR, el SDK de RUM para iOS requiere el valor de consentimiento de seguimiento en la inicialización.

La configuración trackingConsent puede ser uno de los siguientes valores:

  1. .pending: El SDK de RUM para iOS comienza a recopilar y agrupar los datos, pero no los envía a Datadog. El SDK de RUM para iOS espera el nuevo valor de consentimiento de seguimiento para decidir qué hacer con los datos agrupados.
  2. .granted: El SDK de RUM para iOS comienza a recopilar los datos y los envía a Datadog.
  3. .notGranted: El SDK de RUM para iOS no recopila ningún dato. No se envían registros, trazas ni eventos RUM a Datadog.

Para cambiar el valor de consentimiento de seguimiento después de que el SDK de RUM para iOS esté inicializado, utilice la llamada a la API Datadog.set(trackingConsent:). El SDK de RUM para iOS cambia su comportamiento de acuerdo con el nuevo valor.

Por ejemplo, si el consentimiento de seguimiento actual es .pending:

  • Si cambia el valor a .granted, el SDK de RUM para iOS envía todos los datos actuales y futuros a Datadog;
  • Si cambia el valor a .notGranted, el SDK de RUM para iOS elimina todos los datos actuales y no recopila datos futuros.

Agregar propiedades de usuario

Puede usar la Datadog.addUserExtraInfo(_:) API para agregar propiedades de usuario adicionales a las propiedades establecidas anteriormente.

import DatadogCore

Datadog.addUserExtraInfo(["company": "Foo"])

Gestión de datos

El SDK de iOS primero almacena eventos localmente y solo envía eventos cuando se cumplen las condiciones de especificaciones de recepción.

Eliminar todos los datos

Tiene la opción de eliminar todos los datos no enviados almacenados por el SDK con la Datadog.clearAllData() API.

import DatadogCore

Datadog.clearAllData()

Detener la recopilación de datos

Puede usar la Datadog.stopInstance() API para detener una instancia nombrada del SDK (o la instancia predeterminada si el nombre es nil) de recopilar y enviar datos en adelante.

import DatadogCore

Datadog.stopInstance()

Llamar a este método desactiva el SDK y todas las funciones activas, como RUM. Para reanudar la recopilación de datos, debe reinicializar el SDK. Puede usar esta API si desea cambiar configuraciones dinámicamente.

Lectura adicional