AWS X-Ray SDK pour Java - AWS X-Ray

Les traductions sont fournies par des outils de traduction automatique. En cas de conflit entre le contenu d'une traduction et celui de la version originale en anglais, la version anglaise prévaudra.

AWS X-Ray SDK pour Java

Le SDK X-Ray pour Java est un ensemble de bibliothèques Java pour les applications Web qui fournissent des classes et des méthodes permettant de générer et d'envoyer des données de trace au daemon X-Ray. Les données de suivi incluent des informations sur les requêtes HTTP entrantes traitées par l'application et les appels que l'application envoie aux services en aval à l'aide du AWS SDK, des clients HTTP ou d'un connecteur de base de données SQL. Vous pouvez également créer des segments manuellement et ajouter des informations de débogage dans les annotations et les métadonnées.

Le SDK X-Ray pour Java est un projet open source. Vous pouvez suivre le projet et soumettre des problèmes et des pull requests sur GitHub : github.com/aws/ aws-xray-sdk-java

Commencez par ajouter AWSXRayServletFilter en tant que filtre servlet pour suivre les demandes entrantes. Un filtre de servlet crée un segment. Lorsque le segment est ouvert, vous pouvez utiliser les méthodes du client du SDK pour ajouter des informations au segment et créer des sous-segments afin de suivre les appels en aval. Le kit de développement logiciel (SDK) enregistre aussi automatiquement les exceptions que votre application renvoie quand le segment est ouvert.

À partir de la version 1.3, vous pouvez instrumenter votre application à l'aide de la programmation orientée aspect (AOP) dans Spring. Cela signifie que vous pouvez instrumenter votre application pendant qu'elle est en cours d'exécution AWS, sans ajouter de code au runtime de votre application.

Utilisez ensuite le SDK X-Ray pour Java pour instrumenter AWS SDK for Java vos clients en incluant le sous-module SDK Instrumentor dans votre configuration de compilation. Chaque fois que vous appelez une ressource Service AWS ou une ressource en aval avec un client instrumenté, le SDK enregistre les informations relatives à l'appel dans un sous-segment. Services AWS et les ressources auxquelles vous accédez au sein des services apparaissent sous forme de nœuds en aval sur la carte de trace pour vous aider à identifier les erreurs et les problèmes de limitation sur les connexions individuelles.

Si vous ne souhaitez pas instrumenter tous les appels en aval Services AWS, vous pouvez omettre le sous-module Instrumentor et choisir les clients à instrumenter. Instrumentez des clients individuels en ajoutant un TracingHandler à un client de service AWS SDK.

D'autres sous-modules du SDK X-Ray pour Java fournissent une instrumentation pour les appels en aval aux API Web HTTP et aux bases de données SQL. Vous pouvez utiliser le SDK X-Ray pour les versions Java HTTPClient de HTTPClientBuilder et dans le sous-module HTTP Apache pour instrumenter les clients HTTP Apache. Pour instrumenter les requêtes SQL, ajoutez l'intercepteur du kit de développement logiciel (SDK) à votre source de données.

Après avoir commencé à utiliser le SDK, personnalisez son comportement en configurant l'enregistreur et le filtre de servlet. Vous pouvez ajouter des plug-ins pour enregistrer les données sur les ressources de calcul exécutant votre application, personnaliser le comportement d'échantillonnage en définissant des règles d'échantillonnage et définir le niveau de journal afin d'afficher plus ou moins d'informations du kit de développement logiciel dans vos journaux d'application.

Enregistrez les informations supplémentaires sur les demandes et le travail que votre application effectue dans les annotations et les métadonnées. Les annotations sont de simples paires clé-valeur, indexées en vue de leur utilisation avec les expressions de filtre, de telle sorte que vous pouvez explorer les suivis qui contiennent des données spécifiques. Les entrées des métadonnées sont moins restrictives et peuvent enregistrer des objets et tableaux entiers (tout ce qui peut être sérialisé en JSON).

Annotations et métadonnées

Les annotations et les métadonnées sont du texte arbitraire que vous ajoutez aux segments avec le SDK X-Ray. Les annotations sont indexées pour être utilisées avec les expressions de filtre. Les métadonnées ne sont pas indexées, mais peuvent être consultées dans le segment brut à l'aide de la console ou de l'API X-Ray. Toute personne à qui vous accordez un accès en lecture à X-Ray peut consulter ces données.

Lorsque vous avez un grand nombre de clients instrumentés dans votre code, un seul segment de demande peut contenir un grand nombre de sous-segments, un par appel effectué à l'aide d'un client instrumenté. Vous pouvez organiser et grouper les sous-segments en enveloppant les appels clients dans des sous-segments personnalisés. Vous pouvez créer un sous-segment personnalisé pour une fonction complète ou une quelconque section du code, puis enregistrer les métadonnées et les annotations sur le sous-segment au lieu de tout écrire sur le segment parent.

Sous-modules

Vous pouvez télécharger le SDK X-Ray pour Java depuis Maven. Le SDK X-Ray pour Java est divisé en sous-modules par cas d'utilisation, avec une nomenclature pour la gestion des versions :

Si vous utilisez Maven ou Gradle pour créer votre application, ajoutez le SDK X-Ray pour Java à votre configuration de compilation.

Pour la documentation de référence sur les classes et les méthodes du SDK, consultez la section AWS X-Ray SDK pour les références d'JavaAPI.

Prérequis

Le SDK X-Ray pour Java Java nécessite la version 8 ou une version ultérieure, l'API Servlet 3, AWS le SDK et Jackson.

Le kit de développement logiciel dépend des bibliothèques suivantes lors de la compilation et de l'exécution :

  • AWS SDK pour la Java version 1.11.398 ou ultérieure

  • Servlet API 3.1.0

Ces dépendances sont déclarées dans le fichier pom.xml du kit de développement logiciel et sont incluses automatiquement si vous créez à l'aide de Maven ou Gradle.

Si vous utilisez une bibliothèque incluse dans le SDK X-Ray pour Java, vous devez utiliser la version incluse. Par exemple, si vous dépendez déjà de Jackson lors de l'exécution et incluez des fichiers JAR dans votre déploiement pour cette dépendance, vous devez supprimer ces fichiers JAR, car le fichier JAR du kit SDK inclut ses propres versions des bibliothèques Jackson.

Gestion des dépendances

Le SDK X-Ray pour Java est disponible auprès de Maven :

  • Groupecom.amazonaws

  • Artifact — aws-xray-recorder-sdk-bom

  • Version2.11.0

Si vous utilisez Maven pour créer votre application, ajoutez le kit de développement logiciel en tant que dépendance dans votre fichier pom.xml.

Exemple pom.xml - dépendances
<dependencyManagement> <dependencies> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-bom</artifactId> <version>2.11.0</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement> <dependencies> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-core</artifactId> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-apache-http</artifactId> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-aws-sdk</artifactId> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-aws-sdk-instrumentor</artifactId> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-sql-postgres</artifactId> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-sql-mysql</artifactId> </dependency> </dependencies>

Pour Gradle, ajoutez le kit de développement logiciel en tant que dépendance de compilation dans votre fichier build.gradle.

Exemple build.gradle - dépendances
dependencies { compile("org.springframework.boot:spring-boot-starter-web") testCompile("org.springframework.boot:spring-boot-starter-test") compile("com.amazonaws:aws-java-sdk-dynamodb") compile("com.amazonaws:aws-xray-recorder-sdk-core") compile("com.amazonaws:aws-xray-recorder-sdk-aws-sdk") compile("com.amazonaws:aws-xray-recorder-sdk-aws-sdk-instrumentor") compile("com.amazonaws:aws-xray-recorder-sdk-apache-http") compile("com.amazonaws:aws-xray-recorder-sdk-sql-postgres") compile("com.amazonaws:aws-xray-recorder-sdk-sql-mysql") testCompile("junit:junit:4.11") } dependencyManagement { imports { mavenBom('com.amazonaws:aws-java-sdk-bom:1.11.39') mavenBom('com.amazonaws:aws-xray-recorder-sdk-bom:2.11.0') } }

Si vous utilisez Elastic Beanstalk pour déployer votre application, vous pouvez utiliser Maven ou Gradle pour créer sur instance chaque fois que vous déployez, au lieu de créer et de télécharger une archive volumineuse contenant toutes vos dépendances. Consultez l' exemple d'application pour obtenir un exemple utilisant Gradle.

Configuration du SDK X-Ray pour Java

Le SDK X-Ray pour Java inclut une classe AWSXRay nommée qui fournit l'enregistreur global. Ceci est un TracingHandler que vous pouvez utiliser pour outiller votre code. Vous pouvez configurer l'enregistreur mondial pour personnaliser le AWSXRayServletFilter qui crée des segments pour les appels HTTP entrants.

Plug-ins de service

Permet plugins d'enregistrer des informations sur le service hébergeant votre application.

Plugins
  • Amazon EC2 : EC2Plugin ajoute l'ID de l'instance, la zone de disponibilité et le groupe de CloudWatch journaux.

  • Elastic ElasticBeanstalkPlugin Beanstalk : ajoute le nom de l'environnement, l'étiquette de version et l'ID de déploiement.

  • Amazon ECS — ECSPlugin ajoute l'ID du conteneur.

  • Amazon EKS : EKSPlugin ajoute l'ID du conteneur, le nom du cluster, l'ID du pod et le groupe de CloudWatch journaux.

Segmentez les données des ressources avec les plugins Amazon EC2 et Elastic Beanstalk.

Pour utiliser un plug-in, appelez withPlugin sur votre AWSXRayRecorderBuilder.

Exemple src/main/java/scorekeep/ .java - enregistreur WebConfig
import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.AWSXRayRecorderBuilder; import com.amazonaws.xray.plugins.EC2Plugin; import com.amazonaws.xray.plugins.ElasticBeanstalkPlugin; import com.amazonaws.xray.strategy.sampling.LocalizedSamplingStrategy; @Configuration public class WebConfig { ... static { AWSXRayRecorderBuilder builder = AWSXRayRecorderBuilder.standard().withPlugin(new EC2Plugin()).withPlugin(new ElasticBeanstalkPlugin()); URL ruleFile = WebConfig.class.getResource("/sampling-rules.json"); builder.withSamplingStrategy(new LocalizedSamplingStrategy(ruleFile)); AWSXRay.setGlobalRecorder(builder.build()); } }

Le SDK utilise également les paramètres du plugin pour définir le origin champ du segment. Cela indique le type de AWS ressource qui exécute votre application. Lorsque vous utilisez plusieurs plug-ins, le SDK utilise l'ordre de résolution suivant pour déterminer l'origine : ElasticBeanstalk > EKS > ECS > EC2.

Règles d'échantillonnage

Le SDK utilise les règles d'échantillonnage que vous définissez dans la console X-Ray pour déterminer les demandes à enregistrer. La règle par défaut suit la première demande chaque seconde, et 5 % de toutes les demandes supplémentaires provenant de tous les services envoient des traces à X-Ray. Créez des règles supplémentaires dans la console X-Ray pour personnaliser la quantité de données enregistrées pour chacune de vos applications.

Le SDK applique les règles personnalisées dans l'ordre dans lequel elles sont définies. Si une demande correspond à plusieurs règles personnalisées, le SDK applique uniquement la première règle.

Note

Si le SDK ne parvient pas à accéder à X-Ray pour obtenir des règles d'échantillonnage, il revient à une règle locale par défaut concernant la première demande reçue au début de chaque seconde, et 5 % de toutes les demandes supplémentaires par hôte. Cela peut se produire si l'hôte n'est pas autorisé à appeler des API d'échantillonnage ou ne peut pas se connecter au daemon X-Ray, qui agit comme un proxy TCP pour les appels d'API effectués par le SDK.

Vous pouvez également configurer le SDK pour charger des règles d'échantillonnage à partir d'un document JSON. Le SDK peut utiliser les règles locales comme solution de rechange dans les cas où l'échantillonnage X-Ray n'est pas disponible, ou utiliser exclusivement les règles locales.

Exemple sampling-rules.json
{ "version": 2, "rules": [ { "description": "Player moves.", "host": "*", "http_method": "*", "url_path": "/api/move/*", "fixed_target": 0, "rate": 0.05 } ], "default": { "fixed_target": 1, "rate": 0.1 } }

Cet exemple définit une règle personnalisée et une règle par défaut. La règle personnalisée applique un taux d'échantillonnage de 5 % sans nombre minimum de demandes à suivre pour les chemins sous-jacents. /api/move/ La règle par défaut suit la première demande chaque seconde et 10 % des demandes supplémentaires.

L'inconvénient de définir des règles localement est que la cible fixe est appliquée par chaque instance de l'enregistreur indépendamment, au lieu d'être gérée par le service X-Ray. Au fur et à mesure que vous déployez de nouveaux hôtes, le taux fixe est multiplié, ce qui complique le contrôle de la quantité de données enregistrées.

Activé AWS Lambda, vous ne pouvez pas modifier le taux d'échantillonnage. Si votre fonction est appelée par un service instrumenté, les appels ayant généré des demandes échantillonnées par ce service seront enregistrés par Lambda. Si le suivi actif est activé et qu'aucun en-tête de suivi n'est présent, Lambda prend la décision d'échantillonnage.

Pour fournir des règles de sauvegarde dans Spring, configurez l'enregistreur mondial avec une stratégie CentralizedSamplingStrategy dans une classe de configuration.

Exemple src/main/java/myapp/ .java - configuration WebConfig de l'enregistreur
import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.AWSXRayRecorderBuilder; import com.amazonaws.xray.javax.servlet.AWSXRayServletFilter; import com.amazonaws.xray.plugins.EC2Plugin; import com.amazonaws.xray.strategy.sampling.LocalizedSamplingStrategy; @Configuration public class WebConfig { static { AWSXRayRecorderBuilder builder = AWSXRayRecorderBuilder.standard().withPlugin(new EC2Plugin()); URL ruleFile = WebConfig.class.getResource("/sampling-rules.json"); builder.withSamplingStrategy(new CentralizedSamplingStrategy(ruleFile)); AWSXRay.setGlobalRecorder(builder.build()); }

Pour Tomcat, ajoutez un écouteur qui étend ServletContextListener et enregistrez l'écouteur dans le descripteur de déploiement.

Exemple src/com/myapp/web/Startup.java
import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.AWSXRayRecorderBuilder; import com.amazonaws.xray.plugins.EC2Plugin; import com.amazonaws.xray.strategy.sampling.LocalizedSamplingStrategy; import java.net.URL; import javax.servlet.ServletContextEvent; import javax.servlet.ServletContextListener; public class Startup implements ServletContextListener { @Override public void contextInitialized(ServletContextEvent event) { AWSXRayRecorderBuilder builder = AWSXRayRecorderBuilder.standard().withPlugin(new EC2Plugin()); URL ruleFile = Startup.class.getResource("/sampling-rules.json"); builder.withSamplingStrategy(new CentralizedSamplingStrategy(ruleFile)); AWSXRay.setGlobalRecorder(builder.build()); } @Override public void contextDestroyed(ServletContextEvent event) { } }
Exemple WEB-INF/web.xml
... <listener> <listener-class>com.myapp.web.Startup</listener-class> </listener>

Pour utiliser les règles local uniquement, remplacez CentralizedSamplingStrategy par LocalizedSamplingStrategy.

builder.withSamplingStrategy(new LocalizedSamplingStrategy(ruleFile));

Journalisation

Par défaut, le SDK envoie des messages de ERROR niveau B dans les journaux de vos applications. Vous pouvez activer la journalisation au niveau du débogage sur le SDK pour générer des journaux plus détaillés dans le fichier journal de votre application. Les niveaux de journalisation valides sont DEBUG INFOWARN,,ERROR, etFATAL. FATALlog level désactive tous les messages de journal car le SDK ne se journalise pas à un niveau fatal.

Exemple application.properties

Définissez le niveau de journalisation avec la propriété logging.level.com.amazonaws.xray.

logging.level.com.amazonaws.xray = DEBUG

Utilisez les journaux de débogage pour identifier les problèmes, tels que des sous-segments ouverts, lorsque vous générez manuellement des sous-segments.

Injection d'ID de suivi dans les journaux

Pour exposer l'ID de trace complet actuel à vos instructions de journal, vous pouvez l'injecter dans le contexte de diagnostic mappé (MDC). À l'aide de l'interface SegmentListener, les méthodes sont appelées à partir de l'enregistreur X-Ray lors des événements du cycle de vie des segments. Lorsqu'un segment ou un sous-segment commence, l'ID de trace qualifié est injecté dans le MDC avec la clé AWS-XRAY-TRACE-ID. Lorsque ce segment se termine, la clé est supprimée du MDC. Ceci expose l'ID de trace à la bibliothèque de journalisation en cours d'utilisation. Lorsqu'un sous-segment se termine, son ID parent est injecté dans le MDC.

Exemple ID de trace complet

L'ID complet est affiché au format TraceID@EntityID

1-5df42873-011e96598b447dfca814c156@541b3365be3dafc3

Cette fonctionnalité fonctionne avec les applications Java instrumentées avec le SDK AWS X-Ray pour Java et prend en charge les configurations de journalisation suivantes :

  • API frontale SLF4J avec backend Logback

  • API frontale SLF4J avec backend Log4J2

  • API frontale Log4J2 avec backend Log4J2

Consultez les onglets suivants pour connaître les besoins de chaque frontal et de chaque backend.

SLF4J Frontend
  1. Ajoutez la dépendance Maven suivante à votre projet.

    <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-slf4j</artifactId> <version>2.11.0</version> </dependency>
  2. Incluez la méthode withSegmentListener lors de la construction du AWSXRayRecorder. Cela ajoute une classe SegmentListener, qui injecte automatiquement de nouveaux ID de trace dans le MDC SLF4J.

    SegmentListener utilise une chaîne facultative comme paramètre pour configurer le préfixe de l'instruction de journalisation. Le préfixe peut être configuré comme suit :

    • Aucun — Utilise le AWS-XRAY-TRACE-ID préfixe par défaut.

    • Vide — Utilise une chaîne vide (par exemple"").

    • Personnalisé — Utilise un préfixe personnalisé tel que défini dans la chaîne.

    Exemple AWSXRayRecorderBuilder déclaration
    AWSXRayRecorderBuilder builder = AWSXRayRecorderBuilder .standard().withSegmentListener(new SLF4JSegmentListener("CUSTOM-PREFIX"));
Log4J2 front end
  1. Ajoutez la dépendance Maven suivante à votre projet.

    <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-log4j</artifactId> <version>2.11.0</version> </dependency>
  2. Incluez la méthode withSegmentListener lors de la construction du AWSXRayRecorder. Cela ajoutera une classe SegmentListener, qui injecte automatiquement de nouveaux ID de trace complets dans le MDC SLF4J.

    SegmentListener utilise une chaîne facultative comme paramètre pour configurer le préfixe de l'instruction de journalisation. Le préfixe peut être configuré comme suit :

    • Aucun — Utilise le AWS-XRAY-TRACE-ID préfixe par défaut.

    • Vide — Utilise une chaîne vide (par exemple"") et supprime le préfixe.

    • Personnalisé — Utilise le préfixe personnalisé défini dans la chaîne.

    Exemple AWSXRayRecorderBuilder déclaration
    AWSXRayRecorderBuilder builder = AWSXRayRecorderBuilder .standard().withSegmentListener(new Log4JSegmentListener("CUSTOM-PREFIX"));
Logback backend

Pour insérer l'ID de trace dans vos événements de journal, vous devez modifier le PatternLayout de l'enregistreur, qui formate chaque instruction de journalisation.

  1. Recherchez l'emplacement où patternLayout est configuré. Vous pouvez le faire par programme ou via un fichier de configuration XML. Pour en savoir plus, consultez Configuration Logback.

  2. Insérez %X{AWS-XRAY-TRACE-ID} n'importe où dans le patternLayout pour insérer l'ID de trace dans les instructions de journalisation futures. %X{} indique que vous récupérez une valeur avec la clé fournie à partir du MDC. Pour en savoir plus sur PatternLayouts Logback, voir PatternLayout.

Log4J2 backend
  1. Recherchez l'emplacement où patternLayout est configuré. Vous pouvez le faire par programme ou via un fichier de configuration écrit au format XML, JSON, YAML ou propriétés.

    Pour en savoir plus sur la configuration de Log4J2 via un fichier de configuration, consultez Configuration.

    Pour en savoir plus sur la configuration de Log4J2 par programmation, consultez Configuration programmatique.

  2. Insérez %X{AWS-XRAY-TRACE-ID} n'importe où dans le PatternLayout pour insérer l'ID de trace dans les instructions de journalisation futures. %X{} indique que vous récupérez une valeur avec la clé fournie à partir du MDC. Pour en savoir plus sur PatternLayouts Log4J2, consultez Pattern Layout.

Exemple d'injection d'ID de trace

Ce qui suit montre une chaîne PatternLayout modifiée pour inclure l'ID de trace. L'ID de trace est imprimé après le nom du thread (%t) et avant le niveau du journal (%-5p).

Exemple PatternLayout avec injection d'ID
%d{HH:mm:ss.SSS} [%t] %X{AWS-XRAY-TRACE-ID} %-5p %m%n

AWS X-Ray imprime automatiquement la clé et l'identifiant de trace dans l'instruction du journal pour faciliter l'analyse. Ce qui suit montre une instruction de journal à l'aide de la modification de PatternLayout.

Exemple Instruction de journalisation avec injection d'ID
2019-09-10 18:58:30.844 [nio-5000-exec-4] AWS-XRAY-TRACE-ID: 1-5d77f256-19f12e4eaa02e3f76c78f46a@1ce7df03252d99e1 WARN 1 - Your logging message here

Le message de journalisation lui-même est hébergé dans le modèle %m et est défini lors de l'appel de l'enregistreur.

Écouteurs de segment

Les écouteurs de segment sont une interface permettant d'intercepter les événements du cycle de vie tels que le début et la fin des segments générés par AWSXRayRecorder. L'implémentation d'une fonction d'événement d'écouteur de segment peut consister à ajouter la même annotation à tous les sous-segments lorsqu'ils sont créés avec onBeginSubsegment, à journaliser un message une fois que chaque segment est envoyé au démon à l'aide de afterEndSegment, ou à enregistrer les requêtes envoyées par les intercepteurs SQL à l'aide de beforeEndSubsegment pour vérifier si le sous-segment représente une requête SQL, en ajoutant des métadonnées supplémentaires dans ce cas.

Pour consulter la liste complète des SegmentListener fonctions, consultez la documentation de l'API AWS X-Ray Recorder SDK for Java.

L'exemple suivant montre comment ajouter une annotation cohérente à tous les sous-segments lors de la création avec onBeginSubsegment et comment imprimer un message de journal à la fin de chaque segment avec afterEndSegment.

Exemple MySegmentListener.java
import com.amazonaws.xray.entities.Segment; import com.amazonaws.xray.entities.Subsegment; import com.amazonaws.xray.listeners.SegmentListener; public class MySegmentListener implements SegmentListener { ..... @Override public void onBeginSubsegment(Subsegment subsegment) { subsegment.putAnnotation("annotationKey", "annotationValue"); } @Override public void afterEndSegment(Segment segment) { // Be mindful not to mutate the segment logger.info("Segment with ID " + segment.getId()); } }

Cet écouteur de segment personnalisé est ensuite référencé lors de la génération de AWSXRayRecorder.

Exemple AWSXRayRecorderBuilder déclaration
AWSXRayRecorderBuilder builder = AWSXRayRecorderBuilder .standard().withSegmentListener(new MySegmentListener());

Variables d’environnement

Vous pouvez utiliser des variables d'environnement pour configurer le SDK X-Ray pour Java. Le kit SDK prend en charge les variables suivantes.

  • AWS_XRAY_CONTEXT_MISSING— Réglé sur RUNTIME_ERROR pour générer des exceptions lorsque votre code instrumenté tente d'enregistrer des données alors qu'aucun segment n'est ouvert.

    Valeurs valides
    • RUNTIME_ERROR— Lance une exception d'exécution.

    • LOG_ERROR— Enregistrez une erreur et continuez (par défaut).

    • IGNORE_ERROR— Ignorez l'erreur et continuez.

    Des erreurs liées à des segments ou sous-segments manquants peuvent se produire lorsque vous essayez d'utiliser un client instrumenté dans un code de démarrage qui s'exécute lorsqu'aucune demande n'est ouverte, ou dans un code qui génère un nouveau thread.

  • AWS_XRAY_DAEMON_ADDRESS— Définissez l'hôte et le port de l'écouteur du daemon X-Ray. Par défaut, le SDK utilise à la fois 127.0.0.1:2000 les données de trace (UDP) et l'échantillonnage (TCP). Utilisez cette variable si vous avez configuré le démon pour qu'il écoute sur un port différent ou s'il s'exécute sur un autre hôte.

    Format
    • Même portaddress:port

    • Différents portstcp:address:port udp:address:port

  • AWS_LOG_GROUP— Définissez le nom d'un groupe de journaux sur le groupe de journaux associé à votre application. Si votre groupe de journaux utilise le même AWS compte et la même région que votre application, X-Ray recherchera automatiquement les données de segment de votre application à l'aide de ce groupe de journaux spécifié. Pour plus d'informations sur les groupes de journaux, consultez la section Utilisation des groupes de journaux et des flux.

  • AWS_XRAY_TRACING_NAME— Définissez un nom de service que le SDK utilise pour les segments. Remplace le nom de service que vous définissez sur la stratégie d'attribution de noms de segment du filtre servlet.

Les variables d'environnement remplacent les propriétés de système et les valeurs équivalentes définies dans le code.

Propriétés système

Vous pouvez utiliser les propriétés de système en tant qu'alternative JVM aux variables d'environnement. Le kit SDK prend en charge les propriétés suivantes :

  • com.amazonaws.xray.strategy.tracingName— Équivalent àAWS_XRAY_TRACING_NAME.

  • com.amazonaws.xray.emitters.daemonAddress— Équivalent àAWS_XRAY_DAEMON_ADDRESS.

  • com.amazonaws.xray.strategy.contextMissingStrategy— Équivalent àAWS_XRAY_CONTEXT_MISSING.

Si une propriété système et la variable d'environnement équivalente sont toutes les deux définies, c'est la valeur de la variable d'environnement qui est utilisée. Les deux méthodes remplacent les valeurs définies dans le code.

Suivi des demandes entrantes avec le SDK X-Ray pour Java

Vous pouvez utiliser le SDK X-Ray pour suivre les requêtes HTTP entrantes traitées par votre application sur une instance EC2 dans Amazon EC2 ou Amazon AWS Elastic Beanstalk ECS.

Utilisez un Filter pour instrumenter les demandes HTTP entrantes. Lorsque vous ajoutez le filtre de servlet X-Ray à votre application, le SDK X-Ray pour Java crée un segment pour chaque requête échantillonnée. Ce segment comprend la durée, la méthode et l'état de la demande HTTP. L'instrumentation supplémentaire crée des sous-segments sur ce segment.

Note

Pour les AWS Lambda fonctions, Lambda crée un segment pour chaque requête échantillonnée. Pour plus d’informations, consultez AWS Lambda et AWS X-Ray.

Chaque segment porte un nom qui identifie votre application dans la carte des services. Le segment peut être nommé de manière statique ou vous pouvez configurer le SDK pour qu'il soit nommé dynamiquement en fonction de l'en-tête de l'hôte dans la demande entrante. La dénomination dynamique vous permet de regrouper les traces en fonction du nom de domaine indiqué dans la demande et d'appliquer un nom par défaut si le nom ne correspond pas au modèle attendu (par exemple, si l'en-tête de l'hôte est falsifié).

Demandes transmises

Si un équilibreur de charge ou un autre intermédiaire transmet une demande à votre application, X-Ray prend l'adresse IP du client depuis l'X-Forwarded-Foren-tête de la demande plutôt que depuis l'adresse IP source du paquet IP. L'adresse IP du client enregistrée pour une demande transférée peut être falsifiée, elle ne doit donc pas être fiable.

Lorsqu'une demande est transmise, le SDK définit un champ supplémentaire dans le segment pour l'indiquer. Si le segment contient le champ x_forwarded_for défini surtrue, l'adresse IP du client a été extraite de l'X-Forwarded-Foren-tête de la requête HTTP.

Le gestionnaire de messages crée un segment pour chaque demande entrante avec un bloc http contenant les informations suivantes :

  • Méthode HTTP : GET, POST, PUT, DELETE, etc.

  • Adresse du client : adresse IP du client qui a envoyé la demande.

  • Code de réponse : code de réponse HTTP pour la demande terminée.

  • Moment : heure de début (date de réception de la demande) et heure de fin (date d'envoi de la réponse).

  • Agent utilisateur — Le formulaire user-agent de la demande.

  • Longueur du contenu : content-length extrait de la réponse.

Ajout d'un filtre de suivi à votre application (Tomcat)

Pour Tomcat, ajoutez un <filter> aux fichier web.xml de votre projet. Utilisez le paramètre fixedName pour spécifier un nom de service à appliquer aux segments créés pour les demandes entrantes.

Exemple WEB-INF/web.xml - Tomcat
<filter> <filter-name>AWSXRayServletFilter</filter-name> <filter-class>com.amazonaws.xray.javax.servlet.AWSXRayServletFilter</filter-class> <init-param> <param-name>fixedName</param-name> <param-value>MyApp</param-value> </init-param> </filter> <filter-mapping> <filter-name>AWSXRayServletFilter</filter-name> <url-pattern>*</url-pattern> </filter-mapping>

Ajout d'un filtre de suivi à votre application (Spring)

Pour Spring, ajoutez un Filter à votre classe WebConfig. Transmettez le nom du segment au constructeur AWSXRayServletFilter en tant que chaîne.

Exemple src/main/java/myapp/ WebConfig .java - printemps
package myapp; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Bean; import javax.servlet.Filter; import com.amazonaws.xray.javax.servlet.AWSXRayServletFilter; @Configuration public class WebConfig { @Bean public Filter TracingFilter() { return new AWSXRayServletFilter("Scorekeep"); } }

Configuration d'une stratégie d'attribution de noms de segment

AWS X-Ray utilise un nom de service pour identifier votre application et la distinguer des autres applications, bases de données, API externes et AWS ressources utilisées par votre application. Lorsque le SDK X-Ray génère des segments pour les demandes entrantes, il enregistre le nom du service de votre application dans le champ du nom du segment.

Le SDK X-Ray peut nommer les segments d'après le nom d'hôte dans l'en-tête de la requête HTTP. Cependant, cet en-tête peut être falsifié, ce qui peut entraîner la création de nœuds inattendus dans votre carte de service. Pour éviter que le SDK ne nomme les segments de manière incorrecte en raison de demandes contenant des en-têtes d'hôte falsifiés, vous devez spécifier un nom par défaut pour les demandes entrantes.

Si votre application traite des demandes pour plusieurs domaines, vous pouvez configurer le SDK pour qu'il utilise une stratégie de dénomination dynamique afin de refléter cela dans les noms des segments. Une stratégie de dénomination dynamique permet au SDK d'utiliser le nom d'hôte pour les demandes qui correspondent à un modèle attendu et d'appliquer le nom par défaut aux demandes qui ne le sont pas.

Par exemple, il se peut qu'une seule application envoie des demandes à trois sous-domaines : www.example.comapi.example.com, etstatic.example.com. Vous pouvez utiliser une stratégie de dénomination dynamique avec le modèle *.example.com pour identifier les segments de chaque sous-domaine avec un nom différent, ce qui permet d'obtenir trois nœuds de service sur la carte des services. Si votre application reçoit des demandes dont le nom d'hôte ne correspond pas au modèle, vous verrez un quatrième nœud sur la carte des services avec un nom de remplacement que vous spécifiez.

Pour utiliser le même nom pour tous les segments de la demande, spécifiez le nom de votre application lorsque vous initialisez le filtre servlet, comme indiqué dans la section précédente. Cela a le même effet que de créer un correctif SegmentNamingStrategyen l'appelant SegmentNamingStrategy.fixed() et en le transmettant au AWSXRayServletFilterconstructeur.

Note

Vous pouvez remplacer le nom de service par défaut que vous définissez avec la AWS_XRAY_TRACING_NAMEvariable d'environnementVariables d’environnement.

Une stratégie d'attribution de noms dynamique définit un modèle auquel doivent correspondre les noms d'hôte et un nom par défaut à utiliser si le nom d'hôte de la demande HTTP ne correspond pas au modèle. Pour nommer les segments de façon dynamique dans Tomcat, utilisez dynamicNamingRecognizedHosts et dynamicNamingFallbackName pour définir, respectivement, le modèle et le nom par défaut.

Exemple WEB-INF/web.xml - Filtre servlet avec attribution de noms dynamique
<filter> <filter-name>AWSXRayServletFilter</filter-name> <filter-class>com.amazonaws.xray.javax.servlet.AWSXRayServletFilter</filter-class> <init-param> <param-name>dynamicNamingRecognizedHosts</param-name> <param-value>*.example.com</param-value> </init-param> <init-param> <param-name>dynamicNamingFallbackName</param-name> <param-value>MyApp</param-value> </init-param> </filter> <filter-mapping> <filter-name>AWSXRayServletFilter</filter-name> <url-pattern>*</url-pattern> </filter-mapping>

Pour Spring, créez une dynamique SegmentNamingStrategyen appelant SegmentNamingStrategy.dynamic() et transmettez-la au AWSXRayServletFilter constructeur.

Exemple src/main/java/myapp/ .java - filtre WebConfig de servlet avec dénomination dynamique
package myapp; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Bean; import javax.servlet.Filter; import com.amazonaws.xray.javax.servlet.AWSXRayServletFilter; import com.amazonaws.xray.strategy.SegmentNamingStrategy; @Configuration public class WebConfig { @Bean public Filter TracingFilter() { return new AWSXRayServletFilter(SegmentNamingStrategy.dynamic("MyApp", "*.example.com")); } }

Suivi des appels du AWS SDK avec le SDK X-Ray pour Java

Lorsque votre application fait des appels Services AWS pour stocker des données, écrire dans une file d'attente ou envoyer des notifications, le SDK X-Ray pour Java suit les appels en aval dans des sous-segments. Les ressources tracées Services AWS et auxquelles vous accédez au sein de ces services (par exemple, un compartiment Amazon S3 ou une file d'attente Amazon SQS) apparaissent sous forme de nœuds en aval sur la carte de suivi de la console X-Ray.

Le SDK X-Ray pour Java instrumente automatiquement tous les clients du SDK AWS lorsque vous incluez aws-sdk les sous-modules et aws-sdk-instrumentor an dans votre build. Si vous n'incluez pas les sous-modules Instrumentor, vous pouvez choisir d'instrumenter certains clients tout en excluant d'autres.

Pour instrumenter des clients individuels, supprimez le aws-sdk-instrumentor sous-module de votre build et ajoutez-en un XRayClient en tant que TracingHandler sur votre client AWS SDK à l'aide du générateur de clients du service.

Par exemple, pour instrumenter un client AmazonDynamoDB, transmettez un gestionnaire de suivi à AmazonDynamoDBClientBuilder.

Exemple MyModel.java - Client DynamoDB
import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.handlers.TracingHandler; ... public class MyModel { private AmazonDynamoDB client = AmazonDynamoDBClientBuilder.standard() .withRegion(Regions.fromName(System.getenv("AWS_REGION"))) .withRequestHandlers(new TracingHandler(AWSXRay.getGlobalRecorder())) .build(); ...

Pour tous les services, vous pouvez voir le nom de l'API appelée dans la console X-Ray. Pour un sous-ensemble de services, le SDK X-Ray ajoute des informations au segment afin d'améliorer la granularité de la carte des services.

Par exemple, lorsque vous passez un appel avec un client DynamoDB instrumenté, le SDK ajoute le nom de la table au segment pour les appels qui ciblent une table. Dans la console, chaque table apparaît sous la forme d'un nœud distinct dans la carte des services, avec un nœud DynamoDB générique pour les appels qui ne ciblent pas une table.

Exemple Sous-segment pour un appel à DynamoDB pour enregistrer un élément
{ "id": "24756640c0d0978a", "start_time": 1.480305974194E9, "end_time": 1.4803059742E9, "name": "DynamoDB", "namespace": "aws", "http": { "response": { "content_length": 60, "status": 200 } }, "aws": { "table_name": "scorekeep-user", "operation": "UpdateItem", "request_id": "UBQNSO5AEM8T4FDA4RQDEB94OVTDRVV4K4HIRGVJF66Q9ASUAAJG", } }

Lorsque vous accédez aux ressources nommées, les appels vers les services suivants créent des nœuds supplémentaires dans la cartographie des services. Les appels qui ne ciblent pas de ressources spécifiques créent un nœud générique pour le service.

  • Amazon DynamoDB — Nom de la table

  • Amazon Simple Storage Service : nom du compartiment et de la clé

  • Amazon Simple Queue Service — Nom de la file d'attente

Pour instrumenter les appels en aval vers Services AWS AWS SDK for Java 2.2 et versions ultérieures, vous pouvez omettre le aws-xray-recorder-sdk-aws-sdk-v2-instrumentor module de votre configuration de compilation. Incluez plutôt le module aws-xray-recorder-sdk-aws-sdk-v2 module, puis instrumentez les clients individuels en les configurant avec un TracingInterceptor.

Exemple AWS SDK for Java 2.2 et versions ultérieures - intercepteur de traçage
import com.amazonaws.xray.interceptors.TracingInterceptor; import software.amazon.awssdk.core.client.config.ClientOverrideConfiguration import software.amazon.awssdk.services.dynamodb.DynamoDbClient; //... public class MyModel { private DynamoDbClient client = DynamoDbClient.builder() .region(Region.US_WEST_2) .overrideConfiguration(ClientOverrideConfiguration.builder() .addExecutionInterceptor(new TracingInterceptor()) .build() ) .build(); //...

Suivi des appels aux services Web HTTP en aval avec le SDK X-Ray pour Java

Lorsque votre application appelle des microservices ou des API HTTP publiques, vous pouvez utiliser la version de X-Ray SDK pour Java pour HttpClient instrumenter ces appels et ajouter l'API au graphe de service en tant que service en aval.

Le SDK X-Ray pour Java DefaultHttpClient inclut des HttpClientBuilder classes qui peuvent être utilisées à la place des équivalents HttpComponents Apache pour instrumenter les appels HTTP sortants.

  • com.amazonaws.xray.proxies.apache.http.DefaultHttpClient - org.apache.http.impl.client.DefaultHttpClient

  • com.amazonaws.xray.proxies.apache.http.HttpClientBuilder - org.apache.http.impl.client.HttpClientBuilder

Ces bibliothèques se trouvent dans le sous-module aws-xray-recorder-sdk-apache-http.

Vous pouvez remplacer vos relevés d'importation existants par l'équivalent de X-Ray pour instrumenter tous les clients, ou utiliser le nom complet lorsque vous initialisez un client pour instrumenter des clients spécifiques.

Exemple HttpClientBuilder
import com.fasterxml.jackson.databind.ObjectMapper; import org.apache.http.HttpEntity; import org.apache.http.client.methods.CloseableHttpResponse; import org.apache.http.client.methods.HttpGet; import org.apache.http.impl.client.CloseableHttpClient; import org.apache.http.util.EntityUtils; import com.amazonaws.xray.proxies.apache.http.HttpClientBuilder; ... public String randomName() throws IOException { CloseableHttpClient httpclient = HttpClientBuilder.create().build(); HttpGet httpGet = new HttpGet("http://names.example.com/api/"); CloseableHttpResponse response = httpclient.execute(httpGet); try { HttpEntity entity = response.getEntity(); InputStream inputStream = entity.getContent(); ObjectMapper mapper = new ObjectMapper(); Map<String, String> jsonMap = mapper.readValue(inputStream, Map.class); String name = jsonMap.get("name"); EntityUtils.consume(entity); return name; } finally { response.close(); } }

Lorsque vous instrumentez un appel à une API Web en aval, le SDK X-Ray pour Java enregistre un sous-segment contenant des informations sur la requête et la réponse HTTP. X-Ray utilise le sous-segment pour générer un segment inféré pour l'API distante.

Exemple Sous-segment pour un appel HTTP en aval
{ "id": "004f72be19cddc2a", "start_time": 1484786387.131, "end_time": 1484786387.501, "name": "names.example.com", "namespace": "remote", "http": { "request": { "method": "GET", "url": "https://names.example.com/" }, "response": { "content_length": -1, "status": 200 } } }
Exemple Segment déduit pour un appel HTTP en aval
{ "id": "168416dc2ea97781", "name": "names.example.com", "trace_id": "1-62be1272-1b71c4274f39f122afa64eab", "start_time": 1484786387.131, "end_time": 1484786387.501, "parent_id": "004f72be19cddc2a", "http": { "request": { "method": "GET", "url": "https://names.example.com/" }, "response": { "content_length": -1, "status": 200 } }, "inferred": true }

Suivi des requêtes SQL avec le SDK X-Ray pour Java

Intercepteurs SQL

Instrumentez les requêtes de base de données SQL en ajoutant l'intercepteur JDBC du SDK X-Ray pour Java à la configuration de votre source de données.

  • PostgreSQLcom.amazonaws.xray.sql.postgres.TracingInterceptor

  • MySQLcom.amazonaws.xray.sql.mysql.TracingInterceptor

Ces intercepteurs se trouvent respectivement dans les sous-modules aws-xray-recorder-sql-postgres et aws-xray-recorder-sql-mysql. Ils implémentent org.apache.tomcat.jdbc.pool.JdbcInterceptor et sont compatibles avec les groupes de connexion Tomcat.

Note

Les intercepteurs SQL n'enregistrent pas la requête SQL elle-même dans les sous-segments à des fins de sécurité.

Pour Spring, ajoutez l'intercepteur dans un fichier de propriétés et créez la source de données avec le DataSourceBuilder de Spring Boot.

Exemple src/main/java/resources/application.properties - Intercepteur JDBC PostgreSQL
spring.datasource.continue-on-error=true spring.jpa.show-sql=false spring.jpa.hibernate.ddl-auto=create-drop spring.datasource.jdbc-interceptors=com.amazonaws.xray.sql.postgres.TracingInterceptor spring.jpa.database-platform=org.hibernate.dialect.PostgreSQL94Dialect
Exemple src/main/java/myapp/WebConfig.java - Source de données
import org.springframework.boot.autoconfigure.EnableAutoConfiguration; import org.springframework.boot.autoconfigure.jdbc.DataSourceBuilder; import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.data.jpa.repository.config.EnableJpaRepositories; import javax.servlet.Filter; import javax.sql.DataSource; import java.net.URL; @Configuration @EnableAutoConfiguration @EnableJpaRepositories("myapp") public class RdsWebConfig { @Bean @ConfigurationProperties(prefix = "spring.datasource") public DataSource dataSource() { logger.info("Initializing PostgreSQL datasource"); return DataSourceBuilder.create() .driverClassName("org.postgresql.Driver") .url("jdbc:postgresql://" + System.getenv("RDS_HOSTNAME") + ":" + System.getenv("RDS_PORT") + "/ebdb") .username(System.getenv("RDS_USERNAME")) .password(System.getenv("RDS_PASSWORD")) .build(); } ... }

Pour Tomcat, faites appel à setJdbcInterceptors la source de données JDBC en faisant référence à la classe X-Ray SDK for Java.

Exemple src/main/myapp/model.java - Source de données
import org.apache.tomcat.jdbc.pool.DataSource; ... DataSource source = new DataSource(); source.setUrl(url); source.setUsername(user); source.setPassword(password); source.setDriverClassName("com.mysql.jdbc.Driver"); source.setJdbcInterceptors("com.amazonaws.xray.sql.mysql.TracingInterceptor;");

La bibliothèque de sources de données Tomcat JDBC est incluse dans le SDK X-Ray pour Java, mais vous pouvez la déclarer en tant que dépendance fournie pour documenter que vous l'utilisez.

Exemple pom.xml - Source de données JDBC
<dependency> <groupId>org.apache.tomcat</groupId> <artifactId>tomcat-jdbc</artifactId> <version>8.0.36</version> <scope>provided</scope> </dependency>

Décorateur de traçage SQL natif

  • Ajoutez aws-xray-recorder-sdk-sqlà vos dépendances.

  • Décorez la source de données, la connexion ou l'instruction de votre base de données.

    dataSource = TracingDataSource.decorate(dataSource) connection = TracingConnection.decorate(connection) statement = TracingStatement.decorateStatement(statement) preparedStatement = TracingStatement.decoratePreparedStatement(preparedStatement, sql) callableStatement = TracingStatement.decorateCallableStatement(callableStatement, sql)

Génération de sous-segments personnalisés avec le SDK X-Ray pour Java

Les sous-segments étendent le segment d'une trace avec des détails sur le travail effectué afin de répondre à une demande. Chaque fois que vous passez un appel avec un client instrumenté, le SDK X-Ray enregistre les informations générées dans un sous-segment. Vous pouvez créer des sous-segments supplémentaires pour regrouper d'autres sous-segments, pour mesurer les performances d'une section de code ou pour enregistrer des annotations et des métadonnées.

Pour gérer des sous-segments, utilisez les méthodes beginSubsegment et endSubsegment.

Exemple GameModel.java - sous-segment personnalisé
import com.amazonaws.xray.AWSXRay; ... public void saveGame(Game game) throws SessionNotFoundException { // wrap in subsegment Subsegment subsegment = AWSXRay.beginSubsegment("Save Game"); try { // check session String sessionId = game.getSession(); if (sessionModel.loadSession(sessionId) == null ) { throw new SessionNotFoundException(sessionId); } mapper.save(game); } catch (Exception e) { subsegment.addException(e); throw e; } finally { AWSXRay.endSubsegment(); } }

Dans cet exemple, le code du sous-segment charge la session du jeu depuis DynamoDB à l'aide d'une méthode basée sur le modèle de session et utilise le mappeur DynamoDB pour enregistrer le AWS SDK for Java jeu. L'encapsulation de ce code dans un sous-segment fait des appels DynamoDB des enfants du sous-segment dans Save Game la vue de suivi de la console.

Si le code de votre sous-segment lève des exceptions cochées, enveloppez-le dans un bloc try et appelez AWSXRay.endSubsegment() dans un bloc finally pour veiller à ce que le sous-segment soit toujours fermé. Si un sous-segment n'est pas fermé, le segment parent ne peut pas être terminé et ne sera pas envoyé à X-Ray.

Pour le code qui ne génère pas d'exceptions vérifiées, vous pouvez le transmettre AWSXRay.CreateSubsegment en tant que fonction Lambda.

Exemple Sous-segment de la fonction Lambda
import com.amazonaws.xray.AWSXRay; AWSXRay.createSubsegment("getMovies", (subsegment) -> { // function code });

Lorsque vous créez un sous-segment au sein d'un segment ou d'un autre sous-segment, le SDK X-Ray pour Java génère un identifiant et enregistre l'heure de début et de fin.

Exemple Sous-segment avec des métadonnées
"subsegments": [{ "id": "6f1605cd8a07cb70", "start_time": 1.480305974194E9, "end_time": 1.4803059742E9, "name": "Custom subsegment for UserModel.saveUser function", "metadata": { "debug": { "test": "Metadata string from UserModel.saveUser" } },

Pour la programmation asynchrone et multithread, vous devez transmettre manuellement le sous-segment à la endSubsegment() méthode pour vous assurer qu'il est correctement fermé, car le contexte de X-Ray peut être modifié lors de l'exécution asynchrone. Si un sous-segment asynchrone est fermé après la fermeture de son segment parent, cette méthode diffuse automatiquement le segment entier vers le daemon X-Ray.

Exemple Sous-segment asynchrone
@GetMapping("/api") public ResponseEntity<?> api() { CompletableFuture.runAsync(() -> { Subsegment subsegment = AWSXRay.beginSubsegment("Async Work"); try { Thread.sleep(3000); } catch (InterruptedException e) { subsegment.addException(e); throw e; } finally { AWSXRay.endSubsegment(subsegment); } }); return ResponseEntity.ok().build(); }

Ajoutez des annotations et des métadonnées aux segments avec le SDK X-Ray pour Java

Vous pouvez utiliser des annotations et des métadonnées pour enregistrer des informations supplémentaires sur les demandes, l'environnement ou votre application. Vous pouvez ajouter des annotations et des métadonnées aux segments créés par le SDK X-Ray ou aux sous-segments personnalisés que vous créez.

Les annotations sont des paires clé-valeur avec des chaînes, des nombres ou des valeurs booléennes. Les annotations sont indexées pour être utilisées avec les expressions de filtre. Utilisez les annotations pour enregistrer les données que vous souhaitez utiliser pour regrouper les suivis dans la console ou lors de l'appel de l'API GetTraceSummaries.

Les métadonnées sont des paires clé-valeur qui peuvent contenir des valeurs de n'importe quel type, y compris des objets et des listes, mais qui ne sont pas indexées pour être utilisées avec des expressions de filtre. Utilisez les métadonnées pour enregistrer des données supplémentaires que vous souhaitez stocker dans le traçage, mais que vous n'avez pas besoin d'utiliser pour la recherche.

En plus des annotations et des métadonnées, vous pouvez également enregistrer les chaînes d'ID utilisateur sur des segments. Les ID utilisateur sont enregistrés dans un champ distinct des segments et indexés en vue d'une utilisation avec la recherche.

Enregistrer des annotations avec le SDK X-Ray pour Java

Utilisez les annotations pour enregistrer les informations sur les segments ou sous-segments qui doivent être indexés pour la recherche.

Exigences liées aux annotations
  • Clés — La clé d'une annotation X-Ray peut comporter jusqu'à 500 caractères alphanumériques. Vous ne pouvez pas utiliser d'espaces ou de symboles autres que le trait de soulignement (_).

  • Valeurs — La valeur d'une annotation X-Ray peut comporter jusqu'à 1 000 caractères Unicode.

  • Nombre d'annotations : vous pouvez utiliser jusqu'à 50 annotations par trace.

Pour enregistrer les annotations
  1. Obtenez une référence au segment ou sous-segment en cours à partir d'AWSXRay.

    import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.entities.Segment; ... Segment document = AWSXRay.getCurrentSegment();

    or

    import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.entities.Subsegment; ... Subsegment document = AWSXRay.getCurrentSubsegment();
  2. Appelez putAnnotation avec une clé de type chaîne et une valeur de type booléen, numérique ou chaîne.

    document.putAnnotation("mykey", "my value");

Le kit de développement logiciel enregistre les annotations sous forme de paires clé-valeur dans un objet annotations du document de segment. Si vous appelez deux fois putAnnotation avec la même clé, les valeurs précédemment enregistrées sur le même segment ou sous-segment sont remplacées.

Pour rechercher les suivis ayant des annotations avec des valeurs spécifiques, utilisez le mot clé annotations.key dans une expression de filtre.

Exemple src/main/java/scorekeep/GameModel.java— Annotations et métadonnées
import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.entities.Segment; import com.amazonaws.xray.entities.Subsegment; ... public void saveGame(Game game) throws SessionNotFoundException { // wrap in subsegment Subsegment subsegment = AWSXRay.beginSubsegment("## GameModel.saveGame"); try { // check session String sessionId = game.getSession(); if (sessionModel.loadSession(sessionId) == null ) { throw new SessionNotFoundException(sessionId); } Segment segment = AWSXRay.getCurrentSegment(); subsegment.putMetadata("resources", "game", game); segment.putAnnotation("gameid", game.getId()); mapper.save(game); } catch (Exception e) { subsegment.addException(e); throw e; } finally { AWSXRay.endSubsegment(); } }

Enregistrement de métadonnées avec le SDK X-Ray pour Java

Utilisez les métadonnées pour enregistrer des informations sur les segments ou sous-segments qui n'ont pas besoin d'être indexés pour la recherche. Les valeurs des métadonnées peuvent être de type chaîne, valeur numérique, valeur booléenne ou tout objet à même d'être sérialisé en un tableau ou objet JSON.

Pour enregistrer les métadonnées
  1. Obtenez une référence au segment ou sous-segment en cours à partir d'AWSXRay.

    import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.entities.Segment; ... Segment document = AWSXRay.getCurrentSegment();

    or

    import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.entities.Subsegment; ... Subsegment document = AWSXRay.getCurrentSubsegment();
  2. Appelez putMetadata avec un espace de noms de type chaîne, une clé de type chaîne, et une valeur de type booléen, numérique, chaîne ou objet.

    document.putMetadata("my namespace", "my key", "my value");

    or

    Appelez putMetadata avec seulement une clé et une valeur.

    document.putMetadata("my key", "my value");

Si vous ne spécifiez pas d'espace de noms, le kit de développement logiciel utilise default. Si vous appelez deux fois putMetadata avec la même clé, les valeurs précédemment enregistrées sur le même segment ou sous-segment sont remplacées.

Exemple src/main/java/scorekeep/GameModel.java— Annotations et métadonnées
import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.entities.Segment; import com.amazonaws.xray.entities.Subsegment; ... public void saveGame(Game game) throws SessionNotFoundException { // wrap in subsegment Subsegment subsegment = AWSXRay.beginSubsegment("## GameModel.saveGame"); try { // check session String sessionId = game.getSession(); if (sessionModel.loadSession(sessionId) == null ) { throw new SessionNotFoundException(sessionId); } Segment segment = AWSXRay.getCurrentSegment(); subsegment.putMetadata("resources", "game", game); segment.putAnnotation("gameid", game.getId()); mapper.save(game); } catch (Exception e) { subsegment.addException(e); throw e; } finally { AWSXRay.endSubsegment(); } }

Enregistrement des identifiants utilisateur avec le SDK X-Ray pour Java

Enregistrez les ID utilisateur sur les segments de la demande afin d'identifier l'utilisateur à l'origine de la demande.

Pour enregistrer les ID utilisateur
  1. Obtenez une référence au segment en cours à partir d'AWSXRay.

    import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.entities.Segment; ... Segment document = AWSXRay.getCurrentSegment();
  2. Appelez setUser avec l'ID de type chaîne de l'utilisateur ayant envoyé la demande.

    document.setUser("U12345");

Vous pouvez appeler setUser dans vos contrôleurs pour enregistrer l'ID utilisateur dès que votre application commence le traitement d'une demande. Si vous n'utilisez le segment que pour définir l'ID utilisateur, vous pouvez chaîner les appels sur une seule ligne.

Exemple src/main/java/scorekeep/ .java — ID utilisateur MoveController
import com.amazonaws.xray.AWSXRay; ... @RequestMapping(value="/{userId}", method=RequestMethod.POST) public Move newMove(@PathVariable String sessionId, @PathVariable String gameId, @PathVariable String userId, @RequestBody String move) throws SessionNotFoundException, GameNotFoundException, StateNotFoundException, RulesException { AWSXRay.getCurrentSegment().setUser(userId); return moveFactory.newMove(sessionId, gameId, userId, move); }

Pour rechercher les suivis d'un ID utilisateur, utilisez le mot clé user dans une expression de filtre.

AWS X-Ray métriques pour le SDK X-Ray pour Java

Cette rubrique décrit l'espace de AWS X-Ray noms, les métriques et les dimensions. Vous pouvez utiliser le SDK X-Ray pour Java pour publier des métriques CloudWatch Amazon non échantillonnées à partir des segments X-Ray que vous avez collectés. Ces métriques sont dérivées de l'heure de début et de fin du segment, ainsi que des indicateurs d'erreur, de défaillance et d'état de limitation. Utilisez ces métriques de suivi pour exposer les nouvelles tentatives et les problèmes de dépendance dans les sous-segments.

CloudWatch est un référentiel de métriques. Une métrique est le concept fondamental d'un ensemble de points de données chronométré dans le temps CloudWatch et représente ce dernier. Vous publiez (ou Services AWS) publiez des points de données métriques dans CloudWatch lesquels vous extrayez des statistiques sous la forme d'un ensemble ordonné de séries chronologiques.

Les métriques sont uniquement définies par un nom, un espace de noms et une ou plusieurs dimensions. Chaque point de données comporte un horodatage et, le cas échéant, une unité de mesure. Lorsque vous demandez des statistiques, le flux de données renvoyé est identifié par l'espace de noms, le nom de la métrique et la dimension.

Pour plus d'informations à ce sujet CloudWatch, consultez le guide de CloudWatch l'utilisateur Amazon.

CloudWatch Métriques X-Ray

L'espace de noms ServiceMetrics/SDK inclut les métriques suivantes.

Métrique Statistiques disponibles Description Unités

Latency

Moyenne, Minimum, Maximum, Nombre

Différence entre l'heure de début et de fin. Moyenne, minimale et maximale décrivent tous une latence de fonctionnement. Count décrit le nombre d'appels.

Millisecondes

ErrorRate

Average, Sum

Taux de demandes qui ont échoué avec un code d'état 4xx Client Error, entraînant une erreur.

Pourcentage

FaultRate

Average, Sum

Taux de traces qui ont échoué avec un code d'état 5xx Server Error, entraînant une erreur.

Pourcentage

ThrottleRate

Average, Sum

Le taux de traces limitées qui renvoient un code d'état 429. Il s'agit d'un sous-ensemble de la métrique ErrorRate.

Pourcentage

OkRate

Average, Sum

Taux de demandes suivies entraînant un code d'état OK.

Pourcentage

CloudWatch Dimensions du X-Ray

Utilisez les dimensions du tableau suivant pour affiner les mesures renvoyées pour vos Java applications instrumentées X-Ray.

Dimension Description

ServiceType

Type du service, par exemple, AWS::EC2::Instance ou NONE, s'il n'est pas connu.

ServiceName

Nom canonique du service.

Activez les CloudWatch métriques X-Ray

Utilisez la procédure suivante pour activer les métriques de suivi dans votre Java application instrumentée.

Pour configurer les métriques de suivi
  1. Ajoutez le aws-xray-recorder-sdk-metrics package en tant que Apache Maven dépendance. Pour plus d'informations, consultez la section Sous-modules du SDK X-Ray pour Java.

  2. Activez un nouveau dans le MetricsSegmentListener() comme partie intégrante de la construction de l'enregistreur global.

    Exemple src/com/myapp/web/Startup.java
    import com.amazonaws.xray.AWSXRay; import com.amazonaws.xray.AWSXRayRecorderBuilder; import com.amazonaws.xray.plugins.EC2Plugin; import com.amazonaws.xray.plugins.ElasticBeanstalkPlugin; import com.amazonaws.xray.strategy.sampling.LocalizedSamplingStrategy; @Configuration public class WebConfig { ... static { AWSXRayRecorderBuilder builder = AWSXRayRecorderBuilder .standard() .withPlugin(new EC2Plugin()) .withPlugin(new ElasticBeanstalkPlugin()) .withSegmentListener(new MetricsSegmentListener()); URL ruleFile = WebConfig.class.getResource("/sampling-rules.json"); builder.withSamplingStrategy(new LocalizedSamplingStrategy(ruleFile)); AWSXRay.setGlobalRecorder(builder.build()); } }
  3. Déployez l' CloudWatch agent pour collecter des métriques à l'aide d'Amazon Elastic Compute Cloud (Amazon EC2), d'Amazon Elastic Container Service (Amazon ECS) ou d'Amazon Elastic Kubernetes Service (Amazon EKS) :

  4. Configurez le SDK pour communiquer avec l' CloudWatch agent. Par défaut, le SDK communique avec l' CloudWatch agent sur l'adresse127.0.0.1. Vous pouvez configurer d'autres adresses en définissant la variable d'environnement ou la propriété Java sur address:port.

    Exemple Variable d'environnement
    AWS_XRAY_METRICS_DAEMON_ADDRESS=address:port
    Exemple Propriété Java
    com.amazonaws.xray.metrics.daemonAddress=address:port
Pour valider la configuration
  1. Connectez-vous à la CloudWatch console AWS Management Console et ouvrez-la à l'adresse https://console.aws.amazon.com/cloudwatch/.

  2. Ouvrez l'onglet Métriques pour observer le flot de vos métriques.

  3. (Facultatif) Dans la CloudWatch console, sous l'onglet Journaux, ouvrez le groupe de ServiceMetricsSDK journaux. Recherchez un flux de journal correspondant aux métriques de l'hôte et confirmez les messages de journal.

Transmission de contexte de segment entre threads dans une application multithreads

Lorsque vous créez un thread dans l'application, AWSXRayRecorder ne conserve pas de référence au segment ou sous-segment actuel Entity. Si vous utilisez un client instrumenté dans le nouveau thread, le SDK essaie d'écrire sur un segment qui n'existe pas, ce qui provoque un. SegmentNotFoundException

Pour éviter de générer des exceptions pendant le développement, vous pouvez configurer l'enregistreur avec un ContextMissingStrategyqui lui indique de consigner une erreur à la place. Vous pouvez configurer la stratégie en code avec SetContextMissingStrategyune variable d'environnement ou une propriété système ou configurer des options équivalentes avec une variable d'environnement ou une propriété système.

Pour résoudre l'erreur, vous pouvez utiliser un nouveau segment en appelant beginSegment lorsque vous démarrez le thread et endSegment lorsque vous le fermez. Cela fonctionne si vous instrumentez du code qui ne s'exécute pas en réponse à une demande HTTP, à l'image du code qui s'exécute au démarrage de l'application.

Si vous utilisez plusieurs threads pour gérer les demandes entrantes, vous pouvez transmettre le segment ou le sous-segment en cours au nouveau thread et le fournir à l'enregistreur mondial. Cela permet de s'assurer que les informations enregistrées dans le nouveau thread sont associées au même segment que les autres informations enregistrées concernant cette demande. Une fois que le segment est disponible dans le nouveau thread, vous pouvez exécuter n'importe quel exécutable ayant accès au contexte de ce segment à l'aide de la segment.run(() -> { ... }) méthode.

Veuillez consulter Utilisation de clients instrumentés dans les threads de travail pour obtenir un exemple.

Utilisation de X-Ray avec une programmation asynchrone

Le SDK X-Ray pour Java peut être utilisé dans des programmes Java asynchrones avec. SegmentContextExecutors SegmentContextExecutor implémente l'interface Executor, ce qui signifie qu'elle peut être transmise à toutes les opérations asynchrones d'un. CompletableFuture Cela garantit que toutes les opérations asynchrones seront exécutées avec le segment approprié dans son contexte.

Exemple App.java : Passage SegmentContextExecutor à CompletableFuture
DynamoDbAsyncClient client = DynamoDbAsyncClient.create(); AWSXRay.beginSegment(); // ... client.getItem(request).thenComposeAsync(response -> { // If we did not provide the segment context executor, this request would not be traced correctly. return client.getItem(request2); }, SegmentContextExecutors.newSegmentContextExecutor());

AOP avec Spring et le SDK X-Ray pour Java

Cette rubrique décrit comment utiliser le SDK X-Ray et le Spring Framework pour instrumenter votre application sans en modifier la logique de base. Cela signifie qu'il existe désormais un moyen non invasif d'instrumenter vos applications exécutées à AWS distance.

Configuration de Spring

Vous pouvez utiliser Maven ou Gradle pour configurer Spring afin de vous servir d'AOP pour instrumenter votre application.

Si vous utilisez Maven pour créer votre application, ajoutez la dépendance suivante dans votre fichier pom.xml.

<dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-xray-recorder-sdk-spring</artifactId> <version>2.11.0</version> </dependency>

Pour Gradle, ajoutez la dépendance suivante dans votre fichier build.gradle.

compile 'com.amazonaws:aws-xray-recorder-sdk-spring:2.11.0'

Configuration de Spring Boot

Outre la dépendance Spring décrite dans la section précédente, si vous utilisez Spring Boot, ajoutez la dépendance suivante si elle ne figure pas déjà dans votre chemin de classe.

Maven :

<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-aop</artifactId> <version>2.5.2</version> </dependency>

Gradle :

compile 'org.springframework.boot:spring-boot-starter-aop:2.5.2'

Ajouter un filtre de suivi à votre application

Ajoutez un Filter à votre WebConfig classe. Transmettez le nom du segment au constructeur AWSXRayServletFilter en tant que chaîne. Pour plus d'informations sur le suivi des filtres et l'instrumentation des demandes entrantes, consultezSuivi des demandes entrantes avec le SDK X-Ray pour Java.

Exemple src/main/java/myapp/ WebConfig .java - printemps
package myapp; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Bean; import javax.servlet.Filter; import com.amazonaws.xray.javax.servlet.AWSXRayServletFilter; @Configuration public class WebConfig { @Bean public Filter TracingFilter() { return new AWSXRayServletFilter("Scorekeep"); } }

Support à Jakarta

Spring 6 utilise Jakarta au lieu de Javax pour son édition Enterprise. Pour prendre en charge ce nouvel espace de noms, X-Ray a créé un ensemble parallèle de classes qui vivent dans leur propre espace de noms Jakarta.

Pour les classes de filtres, remplacez javax parjakarta. Lorsque vous configurez une stratégie de dénomination de segment, ajoutez-la jakarta avant le nom de classe de stratégie de dénomination, comme dans l'exemple suivant :

package myapp; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Bean; import jakarta.servlet.Filter; import com.amazonaws.xray.jakarta.servlet.AWSXRayServletFilter; import com.amazonaws.xray.strategy.jakarta.SegmentNamingStrategy; @Configuration public class WebConfig { @Bean public Filter TracingFilter() { return new AWSXRayServletFilter(SegmentNamingStrategy.dynamic("Scorekeep")); } }

Annotation de votre code ou implémentation d'une interface

Vos classes doivent soit être annotées avec l'@XRayEnabledannotation, soit implémenter l'XRayTracedinterface. Cela demande au système AOP d'encapsuler les fonctions de la classe affectée pour l'instrumentation X-Ray.

Activation de X-Ray dans votre application

Pour activer le traçage X-Ray dans votre application, votre code doit étendre la classe abstraite BaseAbstractXRayInterceptor en remplaçant les méthodes suivantes.

  • generateMetadata—Cette fonction permet de personnaliser les métadonnées associées à la trace de la fonction en cours. Par défaut, le nom de classe de la fonction d'exécution est enregistré dans les métadonnées. Vous pouvez ajouter des données supplémentaires si vous avez besoin d'informations supplémentaires.

  • xrayEnabledClasses—Cette fonction est vide et doit le rester. Elle sert d'hôte pour un pointcut demandant à l'intercepteur quelles méthodes encapsuler. Définissez le pointcut en spécifiant les classes qui sont annotées avec @XRayEnabled pour effectuer le suivi. L'instruction de pointcut suivante demande à l'intercepteur d'encapsuler tous les beans de contrôleur annotés avec l'annotation @XRayEnabled.

    @Pointcut(“@within(com.amazonaws.xray.spring.aop.XRayEnabled) && bean(*Controller)”)

Si votre projet utilise Spring Data JPA, envisagez d'étendre depuis AbstractXRayInterceptor au lieu deBaseAbstractXRayInterceptor.

Exemple

Le code suivant étend la classe abstraiteBaseAbstractXRayInterceptor.

@Aspect @Component public class XRayInspector extends BaseAbstractXRayInterceptor { @Override protected Map<String, Map<String, Object>> generateMetadata(ProceedingJoinPoint proceedingJoinPoint, Subsegment subsegment) throws Exception { return super.generateMetadata(proceedingJoinPoint, subsegment); } @Override @Pointcut("@within(com.amazonaws.xray.spring.aop.XRayEnabled) && bean(*Controller)") public void xrayEnabledClasses() {} }

Le code suivant est une classe qui sera instrumentée par X-Ray.

@Service @XRayEnabled public class MyServiceImpl implements MyService { private final MyEntityRepository myEntityRepository; @Autowired public MyServiceImpl(MyEntityRepository myEntityRepository) { this.myEntityRepository = myEntityRepository; } @Transactional(readOnly = true) public List<MyEntity> getMyEntities(){ try(Stream<MyEntity> entityStream = this.myEntityRepository.streamAll()){ return entityStream.sorted().collect(Collectors.toList()); } } }

Si vous avez correctement configuré votre application, vous devez voir la pile d'appels complète de l'application, depuis le contrôleur jusqu'aux appels de service, comme illustré dans la capture d'écran suivante de la console.

La pile d'appels complète