Amostragem
A Amostragem é um processo que restringe a quantidade de trechos gerados por um sistema. A configuração de amostragem exata que você deve usar depende das suas necessidades específicas, mas, em geral, você deve tomar uma decisão no início de um rastro e permitir que a decisão de amostragem se propague para outros serviços.
Um Sampler pode ser definido no TracerProvider utilizando o método
WithSampler,
conforme o exemplo a seguir:
provider := trace.NewTracerProvider(
trace.WithSampler(trace.AlwaysSample()),
)
AlwaysSample
e
NeverSample
são valores autoexplicativos. AlwaysSample significa que cada trecho será
amostrado, enquanto NeverSample significa que nenhum trecho será amostrado. Ao
iniciar um projeto, ou em ambiente de desenvolvimento, utilize AlwaysSample.
Outros amostradores disponíveis são:
TraceIDRatioBased, que amostra uma fração dos trechos, com base na fração fornecida ao amostrador. Caso esta fração seja .5, metade de todos os trechos serão amostrados.ParentBased, é um decorador de amostrador que se comporta de maneira diferente, com base no pai do trecho. Caso o trecho não possua um pai, o amostrador decorado é usado para tomar a decisão de amostragem. Por padrão,ParentBasedamostra trechos que possuem pais que foram amostrados, e não amostra trechos cujos pais não foram amostrados.
Por padrão, o Tracer Provider utiliza o amostrador ParentBased com o
amostrador AlwaysSample
Caso esteja em um ambiente de produção, considere utilizar o amostrador
ParentBased com o amostrador TraceIDRatioBased.
Amostradores personalizados
Caso os amostradores nativos não atendam às suas necessidades, você pode criar
um amostrador personalizado implementando a interface Sampler. Um
amostrador personalizado deve implementar dois métodos:
ShouldSample(parameters SamplingParameters) SamplingResult: Toma a decisão de amostragem com base nos parâmetros fornecidos.Description() string: Retorna uma descrição do amostrador.
Em ShouldSample, você deve preservar o tracestate do pai no seu
SamplingResult. Não fazer isso quebra a propagação de contexto em sistemas
distribuídos que dependem do tracestate para transmitir dados de rastro
específicos de fornecedores ou de aplicações.
Extraia o tracestate do contexto do trecho pai:
psc := trace.SpanContextFromContext(parameters.ParentContext)
Repasse psc.TraceState() ao construir o seu SamplingResult.
Exemplo
O exemplo a seguir demonstra um amostrador personalizado que amostra trechos com base no valor de um atributo, preservando corretamente o tracestate:
package main
import (
"context"
"go.opentelemetry.io/otel/attribute"
sdktrace "go.opentelemetry.io/otel/sdk/trace"
"go.opentelemetry.io/otel/trace"
)
// AttributeBasedSampler amostra trechos com base no valor de um atributo.
// Ele sempre amostra trechos com o atributo "high.priority" definido como true.
type AttributeBasedSampler struct {
fallback sdktrace.Sampler
}
// NewAttributeBasedSampler cria um novo AttributeBasedSampler.
func NewAttributeBasedSampler(fallback sdktrace.Sampler) *AttributeBasedSampler {
return &AttributeBasedSampler{fallback: fallback}
}
func (s *AttributeBasedSampler) ShouldSample(p sdktrace.SamplingParameters) sdktrace.SamplingResult {
// Sempre extraia o contexto do trecho pai para obter o tracestate.
psc := trace.SpanContextFromContext(p.ParentContext)
// Verifica se algum atributo indica alta prioridade.
for _, attr := range p.Attributes {
if attr.Key == "high.priority" && attr.Value.AsBool() {
return sdktrace.SamplingResult{
Decision: sdktrace.RecordAndSample,
Attributes: p.Attributes,
// Crítico: preserva o tracestate do pai
Tracestate: psc.TraceState(),
}
}
}
// Recorre ao amostrador padrão para os demais trechos.
result := s.fallback.ShouldSample(p)
// Garante que o tracestate seja preservado mesmo ao usar o fallback.
// Os amostradores nativos já tratam isso, mas é uma boa prática verificar.
return sdktrace.SamplingResult{
Decision: result.Decision,
Attributes: result.Attributes,
Tracestate: psc.TraceState(),
}
}
func (s *AttributeBasedSampler) Description() string {
return "AttributeBasedSampler"
}
Utilizando o seu amostrador personalizado
Você pode utilizar o seu amostrador personalizado com o TracerProvider:
sampler := NewAttributeBasedSampler(sdktrace.TraceIDRatioBased(0.1))
provider := sdktrace.NewTracerProvider(
sdktrace.WithSampler(sampler),
)
Você também pode combiná-lo com o amostrador ParentBased:
provider := sdktrace.NewTracerProvider(
sdktrace.WithSampler(
sdktrace.ParentBased(
NewAttributeBasedSampler(sdktrace.TraceIDRatioBased(0.1)),
),
),
)
Considerações adicionais
Ao implementar amostradores personalizados, tenha em mente os seguintes pontos:
Ignorar a decisão de amostragem do pai: Caso queira respeitar as decisões de amostragem do pai, envolva o seu amostrador com
ParentBasedou verifiquepsc.IsSampled()manualmente.Processamento pesado em ShouldSample: A função
ShouldSampleé chamada de forma síncrona a cada criação de trecho. Evite operações custosas, como chamadas de rede ou processamentos complexos, que possam impactar o desempenho.
Feedback
Esta página foi útil?
Thank you. Your feedback is appreciated!
Please let us know how we can improve this page. Your feedback is appreciated!