Expose Traces as metrics for Prometheus (#12823)

7.20.x
Mykhailo Kuznietsov 2019-03-14 16:00:53 +02:00 committed by GitHub
parent 1711815d2d
commit fdc1b0dcf0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 218 additions and 2 deletions

View File

@ -249,6 +249,10 @@
<groupId>org.eclipse.che.core</groupId>
<artifactId>che-core-tracing-core</artifactId>
</dependency>
<dependency>
<groupId>org.eclipse.che.core</groupId>
<artifactId>che-core-tracing-metrics</artifactId>
</dependency>
<dependency>
<groupId>org.eclipse.che.core</groupId>
<artifactId>che-core-tracing-web</artifactId>

View File

@ -78,6 +78,7 @@ import org.eclipse.che.commons.auth.token.ChainedTokenExtractor;
import org.eclipse.che.commons.auth.token.RequestTokenExtractor;
import org.eclipse.che.core.db.DBTermination;
import org.eclipse.che.core.db.schema.SchemaInitializer;
import org.eclipse.che.core.tracing.metrics.TracingMetricsModule;
import org.eclipse.che.inject.DynaModule;
import org.eclipse.che.mail.template.ST.STTemplateProcessorImpl;
import org.eclipse.che.mail.template.TemplateProcessor;
@ -293,6 +294,10 @@ public class WsMasterModule extends AbstractModule {
install(new WsMasterMetricsModule());
install(new MetricsOverrideBinding());
}
if (Boolean.valueOf(System.getenv("CHE_TRACING_ENABLED"))
&& Boolean.valueOf(System.getenv("CHE_METRICS_ENABLED"))) {
install(new TracingMetricsModule());
}
}
private void configureSingleUserMode(Map<String, String> persistenceProperties) {

View File

@ -29,7 +29,11 @@ public class TracerProvider implements Provider<Tracer> {
private final Tracer tracer;
public TracerProvider() {
this.tracer = TracerResolver.resolveTracer();
this(TracerResolver.resolveTracer());
}
public TracerProvider(Tracer tracer) {
this.tracer = tracer;
GlobalTracer.register(tracer);
}

View File

@ -15,6 +15,7 @@ import com.google.common.annotations.Beta;
import com.google.inject.Inject;
import io.opentracing.Scope;
import io.opentracing.Tracer;
import io.opentracing.tag.Tags;
import java.lang.reflect.Method;
import java.util.Map;
import java.util.WeakHashMap;
@ -47,7 +48,11 @@ public class TracingInterceptor implements MethodInterceptor {
public Object invoke(MethodInvocation invocation) throws Throwable {
String spanName = getSpanName(invocation);
try (Scope scope =
tracer.buildSpan(spanName).asChildOf(tracer.activeSpan()).startActive(true)) {
tracer
.buildSpan(spanName)
.asChildOf(tracer.activeSpan())
.withTag(Tags.SPAN_KIND.getKey(), Tags.SPAN_KIND_SERVER)
.startActive(true)) {
Traced.TagsStack.push();

View File

@ -0,0 +1,58 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Copyright (c) 2012-2018 Red Hat, Inc.
This program and the accompanying materials are made
available under the terms of the Eclipse Public License 2.0
which is available at https://www.eclipse.org/legal/epl-2.0/
SPDX-License-Identifier: EPL-2.0
Contributors:
Red Hat, Inc. - initial API and implementation
-->
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<artifactId>che-core-parent</artifactId>
<groupId>org.eclipse.che.core</groupId>
<version>7.0.0-beta-2.0-SNAPSHOT</version>
</parent>
<artifactId>che-core-tracing-metrics</artifactId>
<name>Che Core :: Tracing :: Metrics</name>
<dependencies>
<dependency>
<groupId>com.google.inject</groupId>
<artifactId>guice</artifactId>
</dependency>
<dependency>
<groupId>io.jaegertracing</groupId>
<artifactId>jaeger-core</artifactId>
</dependency>
<dependency>
<groupId>io.jaegertracing</groupId>
<artifactId>jaeger-micrometer</artifactId>
</dependency>
<dependency>
<groupId>io.opentracing</groupId>
<artifactId>opentracing-api</artifactId>
</dependency>
<dependency>
<groupId>io.opentracing.contrib</groupId>
<artifactId>opentracing-metrics</artifactId>
</dependency>
<dependency>
<groupId>io.opentracing.contrib</groupId>
<artifactId>opentracing-metrics-micrometer</artifactId>
</dependency>
<dependency>
<groupId>javax.inject</groupId>
<artifactId>javax.inject</artifactId>
</dependency>
<dependency>
<groupId>org.eclipse.che.core</groupId>
<artifactId>che-core-tracing-core</artifactId>
</dependency>
</dependencies>
</project>

View File

@ -0,0 +1,52 @@
/*
* Copyright (c) 2012-2018 Red Hat, Inc.
* This program and the accompanying materials are made
* available under the terms of the Eclipse Public License 2.0
* which is available at https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* Red Hat, Inc. - initial API and implementation
*/
package org.eclipse.che.core.tracing.metrics;
import io.jaegertracing.Configuration;
import io.jaegertracing.micrometer.MicrometerMetricsFactory;
import io.opentracing.Tracer;
import io.opentracing.contrib.metrics.Metrics;
import io.opentracing.contrib.metrics.MetricsReporter;
import java.util.Set;
import javax.inject.Inject;
import javax.inject.Provider;
import javax.inject.Singleton;
import org.eclipse.che.core.tracing.TracerProvider;
/**
* Provider of {@link Tracer}, that is integrated with metrics.
*
* <p>Tracer instance is created with custom metrics factory, so it would expose internal metrics to
* prometheus server
*
* <p>Tracer is also wrapped in custom metrics reporter, which would report data about traced spans
* and expose them as prometheus metrics
*/
@Singleton
public class MeteredTracerProvider implements Provider<TracerProvider> {
private TracerProvider tracerProvider;
@Inject
public MeteredTracerProvider(Set<MetricsReporter> metricsReporter) {
MicrometerMetricsFactory internalMetricsFactory = new MicrometerMetricsFactory();
Configuration configuration = Configuration.fromEnv();
Tracer tracer =
configuration.getTracerBuilder().withMetricsFactory(internalMetricsFactory).build();
this.tracerProvider = new TracerProvider(Metrics.decorate(tracer, metricsReporter));
}
@Override
public TracerProvider get() {
return tracerProvider;
}
}

View File

@ -0,0 +1,53 @@
/*
* Copyright (c) 2012-2018 Red Hat, Inc.
* This program and the accompanying materials are made
* available under the terms of the Eclipse Public License 2.0
* which is available at https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* Red Hat, Inc. - initial API and implementation
*/
package org.eclipse.che.core.tracing.metrics;
import io.opentracing.contrib.metrics.micrometer.MicrometerMetricsReporter;
import io.opentracing.tag.Tags;
import javax.inject.Provider;
import javax.inject.Singleton;
/**
* Provider of {@link MicrometerMetricsReporter}, which is responsible for reporting metrics of
* traced spans to prometheus server. Here is also specified configuration as for metrics name and
* tags.
*
* <p>This reporter is configured to report all spans with "span.kind" server, as well as provide
* additional label "http.status_code", if such tag is available in the span.
*
* <p>When defining tags , if "Default value" will be null, then the spans which don't have such
* tag, then will not be reported.
*
* <p>Visit https://github.com/opentracing-contrib/java-metrics to find out about how to configure
* reporter.
*/
@Singleton
public class MicrometerMetricsReporterProvider implements Provider<MicrometerMetricsReporter> {
private static final String TRACING_METRIC_NAME = "che_server_api_tracing_span";
private final MicrometerMetricsReporter micrometerMetricsReporter;
public MicrometerMetricsReporterProvider() {
micrometerMetricsReporter =
MicrometerMetricsReporter.newMetricsReporter()
.withName(TRACING_METRIC_NAME)
.withTagLabel(Tags.SPAN_KIND.getKey(), Tags.SPAN_KIND_SERVER)
.withTagLabel(Tags.HTTP_STATUS.getKey(), "undefined")
.build();
}
@Override
public MicrometerMetricsReporter get() {
return micrometerMetricsReporter;
}
}

View File

@ -0,0 +1,29 @@
/*
* Copyright (c) 2012-2018 Red Hat, Inc.
* This program and the accompanying materials are made
* available under the terms of the Eclipse Public License 2.0
* which is available at https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* Red Hat, Inc. - initial API and implementation
*/
package org.eclipse.che.core.tracing.metrics;
import com.google.inject.AbstractModule;
import com.google.inject.multibindings.Multibinder;
import io.opentracing.contrib.metrics.MetricsReporter;
import org.eclipse.che.core.tracing.TracerProvider;
public class TracingMetricsModule extends AbstractModule {
@Override
protected void configure() {
bind(TracerProvider.class).toProvider(MeteredTracerProvider.class);
Multibinder<MetricsReporter> metricsReporterBinder =
Multibinder.newSetBinder(binder(), MetricsReporter.class);
metricsReporterBinder.addBinding().toProvider(MicrometerMetricsReporterProvider.class);
}
}

View File

@ -40,5 +40,6 @@
<module>che-core-tracing-core</module>
<module>che-core-tracing-web</module>
<module>che-core-metrics-core</module>
<module>che-core-tracing-metrics</module>
</modules>
</project>

View File

@ -783,6 +783,11 @@
<artifactId>che-core-tracing-core</artifactId>
<version>${che.version}</version>
</dependency>
<dependency>
<groupId>org.eclipse.che.core</groupId>
<artifactId>che-core-tracing-metrics</artifactId>
<version>${che.version}</version>
</dependency>
<dependency>
<groupId>org.eclipse.che.core</groupId>
<artifactId>che-core-tracing-web</artifactId>