Lorsque AppSignal reçoit des données de votre application, les traces/transactions sont regroupées selon la combinaison de leur espace de noms et de leur nom d’action.
Par défaut, ces noms d’actions sont automatiquement déterminés en fonction de votre framework (par exemple, Controller#action_name, BackgroundWorker#perform, etc.).
Lorsque le nom d’action déterminé automatiquement n’est pas suffisant, vous pouvez le personnaliser.
Ce guide explique comment personnaliser les noms d’actions dans différentes intégrations de langages.
Les noms d’actions ne sont pas censés être uniques !
N’utilisez pas de variables pour personnaliser les noms d’actions, car cela créera un nouvel incident à chaque occurrence.
Cela rend la vue d’ensemble des incidents difficile à utiliser et empêche un regroupement adéquat ainsi qu’une analyse des tendances.Utilisez toujours des chaînes statiques pour les noms d’actions. N’interpolez jamais de variables, d’entrées utilisateur ou de données dynamiques dans les noms d’actions.
Pourquoi personnaliser les noms d’actions ?
- Clarté améliorée : fournissez des noms plus descriptifs pour des opérations complexes.
- Regroupement personnalisé : contrôlez la façon dont les données de l’application sont organisées dans AppSignal.
Lorsque les noms d’actions automatiques sont insuffisants
Voici quelques exemples où les noms d’actions générés automatiquement peuvent être insuffisants :
- Routes fourre-tout : dans les applications qui utilisent des routes fourre-tout ou un routage dynamique (comme
/api/:entity/:action), le nom d’action par défaut peut être quelque chose de générique comme ApiController#dispatch.
- Tâches polyvalentes : les workers d’arrière-plan et les scripts qui gèrent différents types de travail en fonction de paramètres seraient tous regroupés sous le même nom d’action (par exemple,
GenericWorker#perform).
- Resolvers GraphQL : ceux-ci peuvent tous être regroupés sous un seul nom d’action (par exemple,
POST /graphql) bien qu’ils gèrent de nombreux types d’opérations différents.
Personnalisation des actions par langage
Ruby
Dans les applications Ruby, vous pouvez utiliser l’assistant Appsignal.set_action pour personnaliser le nom de l’action :
# In a Rails controller
class PaymentsController < ApplicationController
def process_payment
provider = params[:payment][:provider]
# GOOD: Change the action name from "PaymentsController#process_payment"
# to something more specific about the operation
if provider == "creditcard"
Appsignal.set_action("PaymentsController#process_payment (creditcard)")
end
# BAD: Don't use a dynamic value, it creates too many action names
# Appsignal.set_action("PaymentsController#process_#{provider}")
# Rest of your code
end
end
Pour les jobs en arrière-plan, les tâches et les scripts, vous pouvez définir le nom de l’action de la même manière avec l’assistant Appsignal.set_action.
Il est également possible de configurer le nom de l’action lors de la création d’une transaction à l’aide de l’assistant Appsignal.monitor. Il accepte le nom de l’action comme argument nommé.
# When creating a new transaction
Appsignal.monitor(action: "script/custom_script") do
# Your code to instrument
end
Elixir
Dans les applications Elixir, vous pouvez utiliser la fonction Appsignal.Span.set_name/2 pour personnaliser le nom de l’action sur le span racine :
# In a Phoenix controller
defmodule MyAppWeb.PaymentController do
use MyAppWeb, :controller
def process(conn, params) do
# GOOD: Set a custom static action name based on payment type
payment_type = Map.get(params, "type", "unknown")
if payment_type == "creditcard" do
Appsignal.Span.set_name(
Appsignal.Tracer.root_span(),
"PaymentController#process_payment (creditcard)"
)
end
# BAD: Don't use a dynamic value, it creates too many action names
# Appsignal.Span.set_name(
# Appsignal.Tracer.root_span(),
# "PaymentController#process_#{payment_type}"
# )
# Rest of your code
render(conn, "success.html")
end
end
Pour les jobs en arrière-plan, les tâches et les scripts, vous pouvez définir le nom de l’action de la même manière avec la fonction Appsignal.Span.set_name/2.
Node.js
Dans les applications Node.js, vous pouvez utiliser l’assistant setRootName du package AppSignal pour personnaliser les noms d’actions :
import { setRootName } from "@appsignal/nodejs";
// In an Express.js route handler
app.post("/payments", (req, res) => {
const paymentType = req.body.type || "unknown";
// GOOD: Set a custom action name based on payment type
if (paymentType === "creditcard") {
setRootName("PaymentsController#process_payment (creditcard)");
}
// BAD: Don't use a dynamic value, it creates too many action names
// setRootName(`PaymentsController#process_${paymentType}`);
// Rest of your code
res.send("Payment processed");
});
Pour les jobs en arrière-plan, les tâches et les scripts, vous pouvez définir le nom de l’action de la même manière avec l’assistant setRootName.
Python
Dans les applications Python, vous pouvez utiliser l’assistant set_root_name du package AppSignal pour personnaliser les noms d’actions :
from appsignal import set_root_name
# In a Django view
def process_payment(request):
payment_type = request.POST.get('type', 'unknown')
# GOOD: Set a custom action name based on payment type
if payment_type == "creditcard":
set_root_name("PaymentsView#process_payment (creditcard)")
# BAD: Don't use a dynamic value, it creates too many action names
# set_root_name(f"PaymentsView#process_{payment_type}")
# Rest of your code
return HttpResponse("Payment processed")
Pour les jobs en arrière-plan, les tâches et les scripts, vous pouvez définir le nom de l’action de la même manière avec l’assistant set_root_name.
JavaScript front-end
Dans les applications JavaScript front-end, vous pouvez utiliser l’assistant setAction du package AppSignal pour personnaliser les noms d’actions :
const span = appsignal.createSpan((span) => {
const formType = getFormType();
// GOOD: Set a custom action name based on form type
if (formType === "checkout") {
span.setAction("CheckoutPage#submit_form (checkout)");
}
// BAD: Don't use a dynamic value, it creates too many action names
// span.setAction(`CheckoutPage#submit_${formType}_form`);
// Rest of your code
});
Vous pouvez également mettre à jour le nom d’action d’un span existant :
// Get the current active span
const span = appsignal.getActiveSpan();
function handlePaymentMethodSelection(method) {
// GOOD: Set a custom action name based on payment method
if (method === "creditcard") {
span.setAction("PaymentForm#select_method (creditcard)");
}
// BAD: Don't do this - using a variable creates too many action names
// span.setAction(`PaymentForm#select_${method}`);
// Rest of your code
}
Dans les applications Go, AppSignal fonctionne avec OpenTelemetry, qui utilise des spans pour suivre les métadonnées, comme le nom de l’action. Sur n’importe quel span de la trace, définissez un attribut appsignal.action_name avec une valeur de type String pour personnaliser le nom de l’action :
package main
import (
"context"
"net/http"
"go.opentelemetry.io/otel/attribute"
"go.opentelemetry.io/otel/trace"
)
func processPaymentHandler(w http.ResponseWriter, r *http.Request) {
ctx := r.Context()
span := trace.SpanFromContext(ctx)
paymentType := r.FormValue("type")
// GOOD: Set a custom action name based on payment type
if paymentType == "creditcard" {
span.SetAttributes(attribute.String("appsignal.action_name", "PaymentHandler#process_payment (creditcard)"))
}
// BAD: Don't use a dynamic value, it creates too many action names
// span.SetAttributes(attribute.String("appsignal.action_name", fmt.Sprintf("PaymentHandler#process_%s", paymentType)))
// Rest of your code
w.WriteHeader(http.StatusOK)
w.Write([]byte("Payment processed"))
}
Pour les jobs en arrière-plan, les tâches et les scripts, vous pouvez définir le nom de l’action de la même manière en définissant l’attribut appsignal.action_name sur le span actif.
Java
Dans les applications Java, AppSignal fonctionne avec OpenTelemetry, qui utilise des spans pour suivre les métadonnées, comme le nom de l’action. Sur n’importe quel span de la trace, définissez un attribut appsignal.action_name avec une valeur de type String pour personnaliser le nom de l’action :
import io.opentelemetry.api.trace.Span;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class PaymentController {
@PostMapping("/payments")
public String processPayment(@RequestParam String type) {
Span span = Span.current();
// GOOD: Set a custom action name based on payment type
if ("creditcard".equals(type)) {
span.setAttribute("appsignal.action_name", "PaymentController#processPayment (creditcard)");
}
// BAD: Don't use a dynamic value, it creates too many action names
// span.setAttribute("appsignal.action_name", "PaymentController#process_" + type);
// Rest of your code
return "Payment processed";
}
}
Pour les jobs en arrière-plan, les tâches et les scripts, vous pouvez définir le nom de l’action de la même manière en définissant l’attribut appsignal.action_name sur le span actif.
PHP
Dans les applications PHP, vous pouvez utiliser la méthode d’assistance Appsignal::setAction() du package AppSignal pour personnaliser les noms d’actions :
<?php
use Appsignal\Appsignal;
class PaymentController
{
public function processPayment()
{
$paymentType = $_POST['type'] ?? 'unknown';
// GOOD: Set a custom action name based on payment type
if ($paymentType === 'creditcard') {
Appsignal::setAction('PaymentController::processPayment (creditcard)');
}
// BAD: Don't use a dynamic value, it creates too many action names
// Appsignal::setAction("PaymentController::process_{$paymentType}");
// Rest of your code
return 'Payment processed';
}
}
Pour les jobs en arrière-plan, les tâches et les scripts, vous pouvez définir le nom de l’action de la même manière en définissant l’attribut appsignal.action_name sur le span actif.
Bonnes pratiques
Lors de la personnalisation des noms d’actions, suivez ces recommandations :
- Soyez cohérent : utilisez un schéma de nommage cohérent dans toute votre application.
- Soyez précis : incluez des informations pertinentes qui aident à identifier l’opération.
- Évitez une cardinalité élevée : n’incluez pas d’identifiants ou de valeurs uniques qui créeraient des noms d’actions uniques à chaque exécution.
- Utilisez des chaînes statiques : n’interpolez jamais de variables ou de données dynamiques dans les noms d’actions.
- Suivez le nommage du code : utilisez des schémas de nommage comme
Controller#action qui correspondent à la structure de votre application afin que l’emplacement dans le code puisse être retrouvé.
- Utilisez plutôt des tags ou des métadonnées : pour suivre des informations variables comme les fournisseurs de paiement ou les types d’utilisateurs, utilisez les tags et les métadonnées plutôt que de les intégrer dans les noms d’actions.
Au lieu de créer des noms d’actions dynamiques, utilisez une combinaison de :
- Noms d’actions statiques : utilisez des noms d’actions descriptifs mais statiques.
- Tags : ajoutez des tags avec les informations variables (par exemple,
provider: stripe, operation_type: refund).
- Attributs personnalisés : ajoutez des métadonnées supplémentaires à la trace/transaction.
Exemple :
# Instead of this:
# Appsignal.set_action("PaymentController#process_#{provider}")
# Do this:
Appsignal.set_action("PaymentController#process_payment")
Appsignal.add_tags(
provider: provider,
operation: operation
)
Cette approche vous permet de :
- Regrouper les opérations associées sous un même nom d’action.
- Filtrer et rechercher en fonction des tags.
- Maintenir une vue d’ensemble des incidents propre.
Déployer
Après avoir mis en place des noms d’actions personnalisés, déployez votre application. Les nouvelles traces/transactions utiliseront vos noms d’actions personnalisés dans les tableaux de bord AppSignal.
Les données historiques utiliseront toujours les noms d’actions d’origine. Seules les actions nouvellement rapportées utiliseront les noms personnalisés que vous avez définis.
Vos noms d’actions personnalisés n’apparaissent pas correctement ? N’hésitez pas à contacter notre équipe d’assistance pour obtenir de l’aide !
Pour aller plus loin