In einer Microservice-Umgebung sehe ich zwei Hauptvorteile durch die Verfolgung von Anfragen durch alle Microservice-Instanzen über einen gesamten Geschäftsprozess.Spring Sleuth - Tracing Failures
- Finding Latenz Lücken zwischen oder in Dienstinstanzen
- Finding Wurzeln von Fehlern, ob technischer oder in Bezug auf das Business Case
Mit Zipkin gibt es ein Werkzeug, das das erste Problem behebt. Aber wie kann das Tracing genutzt werden, um Fehler in Ihrer Microservice-Landschaft aufzudecken? Ich möchte definitiv alle fehlerbehafteten Spannen verfolgen, aber nicht jede Anfrage, bei der nichts schief gelaufen ist. Wie erwähnt here könnte ein benutzerdefinierter Sampler verwendet werden.
Alternativ können Sie Ihre eigene Sampler-Bean-Definition registrieren und programmatisch die Entscheidung treffen, die Anfragen abgetastet werden soll. Sie können intelligentere Entscheidungen treffen, welche Dinge zu verfolgen sind, zum Beispiel, indem Sie erfolgreiche Anfragen ignorieren, vielleicht prüfen, ob sich eine Komponente in einem Fehlerzustand befindet, oder wirklich irgendetwas anderes.
Also habe ich versucht, das zu implementieren, aber es funktioniert nicht oder ich habe es falsch verwendet. So , wie die Blog-Post vorgeschlagen registrierte ich meine eigenen Sampler:
@Bean
Sampler customSampler() {
return new Sampler() {
@Override
public boolean isSampled(Span span) {
boolean isErrorSpan = false;
for(String tagKey : span.tags().keySet()){
if(tagKey.startsWith("error_")){
isErrorSpan = true;
}
}
return isErrorSpan ;
}
};
}
Und in meinem Controller erstelle ich einen neuen Span, der als Fehler markiert wird, wenn eine Ausnahme wirft
private final Tracer tracer;
@Autowired
public DemoController(Tracer tracer) {
this.tracer = tracer;
}
@RequestMapping(value = "/calc/{i}")
public String calc(@PathVariable String i){
Span span = null;
try {
span = this.tracer.createSpan("my_business_logic");
return "1/" + i + " = " + new Float(1.0/Integer.parseInt(i)).toString();
}catch(Exception ex){
log.error(ex.getMessage(), ex);
span.logEvent("ERROR: " + ex.getMessage());
this.tracer.addTag("error_" + ex.hashCode(), ex.getMessage());
throw ex;
}
finally{
this.tracer.close(span);
}
}
Jetzt , das funktioniert nicht. Wenn ich/calc/a anfordere, wird die Methode Sampler.isSampled (Span) aufgerufen, bevor die Controller-Methode eine NumberFormatException auslöst. Das bedeutet, wenn isSampled() den Span überprüft, hat es noch keine Tags. Und die Sampler-Methode wird später im Prozess nicht erneut aufgerufen. Nur wenn ich den Sampler öffne und erlaube, dass jeder Bereich abgetastet wird, sehe ich später meine getaggte Fehlerspanne in Zipkin. In diesem Fall wurde Sampler.isSampled (Span) nur einmal aufgerufen, aber HttpZipkinSpanReporter.report (Span) wurde dreimal ausgeführt.
Wie also würde der Anwendungsfall aussehen, nur Traces zu übertragen, die Fehlerspannen haben? Ist dies sogar eine korrekte Methode, um einen Bereich mit einem beliebigen "error_" -Tag zu versehen?
Ok, dann habe ich Sampler.isSampled (Span span) falsch interpretiert, weil nur der erste Span einer Anfrage, die eine Microservice-Barriere erreicht, von einem Sampler betrachtet wird. Ich nehme aus Ihrer Antwort, dass Sleuth nicht für die Fehlersuche verwendet werden sollte, wie im spring.io-Blogpost erwähnt, erwähnte ich. Ist es jedoch möglich, von einer Spanne auf den aktuellen HTTP-Status zuzugreifen, oder besser: den gesamten HTTP-Header?In diesem Fall könnte ich nur Anfragen mit einem Fehlerstatus an zipkin melden. – Danny
Das stimmt nicht. Sie können * auch * Sleuth verwenden, um Fehler zu verfolgen. Beachten Sie, dass Sie in Zipkin aufgrund von Sampling nur (standardmäßig) 10% der Traces sehen, so dass Sie einen Fehler verfolgen können, wenn Sie ihn tatsächlich abtasten. Mit der Version 1.2.0 Sleuth können Sie Gepäck benutzen. Dort können Sie setzen, was Sie wollen und dieser Kontext wird durch das ganze System weiter verbreitet. –
@marcin isSampled wird für jeden Bereich aufgerufen werden, oder? Wenn ich Impl von PercentageBasedSampler sehe, gibt es eine Wahrscheinlichkeit, dass wenige Spannen in einer Spur verpasst werden. Ist das nicht richtig? –