All Downloads are FREE. Search and download functionalities are using the official Maven repository.

io.opentelemetry.exporter.zipkin.ZipkinSpanExporter Maven / Gradle / Ivy

There is a newer version: 1.44.1
Show newest version
/*
 * Copyright The OpenTelemetry Authors
 * SPDX-License-Identifier: Apache-2.0
 */

package io.opentelemetry.exporter.zipkin;

import io.opentelemetry.api.metrics.MeterProvider;
import io.opentelemetry.exporter.internal.ExporterMetrics;
import io.opentelemetry.sdk.common.CompletableResultCode;
import io.opentelemetry.sdk.internal.ThrottlingLogger;
import io.opentelemetry.sdk.trace.data.SpanData;
import io.opentelemetry.sdk.trace.export.SpanExporter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.function.Supplier;
import java.util.logging.Level;
import java.util.logging.Logger;
import zipkin2.Span;
import zipkin2.reporter.BytesEncoder;
import zipkin2.reporter.BytesMessageSender;
import zipkin2.reporter.Encoding;

/**
 * This class was based on the OpenCensus
 * zipkin exporter code.
 */
public final class ZipkinSpanExporter implements SpanExporter {

  public static final Logger baseLogger = Logger.getLogger(ZipkinSpanExporter.class.getName());

  public static final String DEFAULT_ENDPOINT = "http://localhost:9411/api/v2/spans";

  private final ThrottlingLogger logger = new ThrottlingLogger(baseLogger);
  private final AtomicBoolean isShutdown = new AtomicBoolean();
  private final ZipkinSpanExporterBuilder builder;
  private final BytesEncoder encoder;
  private final BytesMessageSender sender;
  private final ExporterMetrics exporterMetrics;

  private final OtelToZipkinSpanTransformer transformer;

  ZipkinSpanExporter(
      ZipkinSpanExporterBuilder builder,
      BytesEncoder encoder,
      BytesMessageSender sender,
      Supplier meterProviderSupplier,
      OtelToZipkinSpanTransformer transformer) {
    this.builder = builder;
    this.encoder = encoder;
    this.sender = sender;
    this.exporterMetrics =
        sender.encoding() == Encoding.JSON
            ? ExporterMetrics.createHttpJson("zipkin", "span", meterProviderSupplier)
            : ExporterMetrics.createHttpProtobuf("zipkin", "span", meterProviderSupplier);
    this.transformer = transformer;
  }

  @Override
  public CompletableResultCode export(Collection spanDataList) {
    if (isShutdown.get()) {
      return CompletableResultCode.ofFailure();
    }

    int numItems = spanDataList.size();
    exporterMetrics.addSeen(numItems);

    List encodedSpans = new ArrayList<>(numItems);
    for (SpanData spanData : spanDataList) {
      Span zipkinSpan = transformer.generateSpan(spanData);
      encodedSpans.add(encoder.encode(zipkinSpan));
    }

    try {
      sender.send(encodedSpans);
      exporterMetrics.addSuccess(numItems);
      return CompletableResultCode.ofSuccess();
    } catch (IOException | RuntimeException t) {
      exporterMetrics.addFailed(numItems);
      logger.log(Level.WARNING, "Failed to export spans", t);
      return CompletableResultCode.ofFailure();
    }
  }

  @Override
  public CompletableResultCode flush() {
    // nothing required here
    return CompletableResultCode.ofSuccess();
  }

  @Override
  public CompletableResultCode shutdown() {
    if (!isShutdown.compareAndSet(false, true)) {
      logger.log(Level.INFO, "Calling shutdown() multiple times.");
      return CompletableResultCode.ofSuccess();
    }
    try {
      sender.close();
    } catch (IOException e) {
      logger.log(Level.WARNING, "Exception while closing the Zipkin Sender instance", e);
    }
    return CompletableResultCode.ofSuccess();
  }

  @Override
  public String toString() {
    return "ZipkinSpanExporter{" + builder.toString(false) + "}";
  }

  /**
   * Returns a new Builder for {@link ZipkinSpanExporter}.
   *
   * @return a new {@link ZipkinSpanExporter}.
   */
  public static ZipkinSpanExporterBuilder builder() {
    return new ZipkinSpanExporterBuilder();
  }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy