From 232801ab624d34849aec910efd0c32f859878755 Mon Sep 17 00:00:00 2001 From: Tyler Benson Date: Wed, 12 Jul 2017 14:28:06 -0700 Subject: [PATCH 1/7] Another pass on improving the docs --- README.md | 13 +- .../ElasticsearchIntegrationTest.java | 156 +++++++++--------- dd-java-agent/README.md | 50 +++--- .../integration/DDAgentTracingHelper.java | 2 +- dd-trace-examples/README.md | 2 +- dd-trace-examples/async-tracing/README.md | 10 +- dd-trace/README.md | 73 ++++---- dd-trace/docs/opentracing-api.md | 16 +- 8 files changed, 164 insertions(+), 158 deletions(-) diff --git a/README.md b/README.md index 26bddc4add..670e25c87e 100644 --- a/README.md +++ b/README.md @@ -13,12 +13,13 @@ gather all traces in your [Datadog](https://app.datadoghq.com) account. ### Start in minutes -* [Introduction to the Datadog APM](https://www.datadoghq.com/apm/). Learn what you can do with the Next-Gen APM and how to get started. -* [Install the Datadog Java agent](dd-java-agent). Instructions for supported technologies, web-servers and frameworks. -* [Browse examples](dd-trace-examples). See how to instrument legacy projects based on the most used tehcnologies. -* [Instrument with OpenTracing](https://github.com/opentracing/opentracing-java). Datadog embraces the OpenTracing initiative. So feel free to use the Trace Java API to customize your instrumentation. -* [DD Trace](dd-trace). This Java implementation of the opentracing api is used to report traces to Datadog. +* [Introduction to the Datadog APM](https://www.datadoghq.com/apm/) - Learn what you can do with the Next-Gen APM and how to get started. +* [Install the Datadog Java agent](dd-java-agent) - Instructions for supported technologies, web-servers and frameworks. +* [Browse examples](dd-trace-examples) - See how to instrument legacy projects based on the most used tehcnologies. +* [Instrument with OpenTracing](https://github.com/opentracing/opentracing-java) - Datadog embraces the OpenTracing initiative. So feel free to use the Trace Java API to customize your instrumentation. +* [DD Trace](dd-trace) - Datadog's implementation of the OpenTracing API for reporting traces to the [Datadog agent](https://github.com/DataDog/datadog-trace-agent). Can be used independently from dd-java-agent. ### Help or questions? -And for any questions or feedback, feel free to send us an email: support@datadoghq.com \ No newline at end of file +For any questions or feedback, feel free to send us an email: support@datadoghq.com +You can also ask for help in the datadoghq slack channel: #apm-java diff --git a/dd-java-agent-ittests/src/test/java/com/datadoghq/trace/agent/integration/ElasticsearchIntegrationTest.java b/dd-java-agent-ittests/src/test/java/com/datadoghq/trace/agent/integration/ElasticsearchIntegrationTest.java index 1d9bffe909..2be0c0b87b 100644 --- a/dd-java-agent-ittests/src/test/java/com/datadoghq/trace/agent/integration/ElasticsearchIntegrationTest.java +++ b/dd-java-agent-ittests/src/test/java/com/datadoghq/trace/agent/integration/ElasticsearchIntegrationTest.java @@ -1,5 +1,5 @@ -//package com.datadoghq.trace.instrument; -// +package com.datadoghq.trace.agent.integration; + //import com.datadoghq.trace.DDTracer; //import com.datadoghq.trace.writer.ListWriter; //import org.elasticsearch.action.index.IndexResponse; @@ -25,79 +25,79 @@ //import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder; // // -//public class ElasticsearchIntegrationTest { -// -// -// private static ListWriter writer = new ListWriter(); -// private static DDTracer tracer = new DDTracer(writer); -// private static final int HTTP_PORT = 9205; -// private static final String HTTP_TRANSPORT_PORT = "9300"; -// private static final String ES_WORKING_DIR = "target/es"; -// private static String clusterName = "elasticsearch"; -// private static Node node; -// -// -// @AfterClass -// public static void stopElasticsearch() throws Exception { -// node.close(); -// } -// -// @BeforeClass -// public static void warmup() throws NodeValidationException { -// -// -// //GlobalTracer.register(tracer); -// -// -// Settings settings = Settings.builder() -// .put("path.home", ES_WORKING_DIR) -// .put("path.data", ES_WORKING_DIR + "/data") -// .put("path.logs", ES_WORKING_DIR + "/logs") -// .put("transport.type", "netty4") -// .put("http.type", "netty4") -// .put("cluster.name", clusterName) -// .put("http.port", HTTP_PORT) -// .put("transport.tcp.port", HTTP_TRANSPORT_PORT) -// .put("network.host", "0.0.0.0") -// .build(); -// Collection plugins = Collections.singletonList(Netty4Plugin.class); -// node = new PluginConfigurableNode(settings, plugins); -// node.start(); -// } -// -// -// @Test -// public void testTransportClient() throws IOException { -// -// -// Settings settings = Settings.builder() -// .put("cluster.name", clusterName).build(); -// -// TransportClient client = new PreBuiltTransportClient(settings) -// .addTransportAddress(new InetSocketTransportAddress(Inet4Address.getByName("localhost"), Integer.parseInt(HTTP_TRANSPORT_PORT))); -// -// IndexResponse response = client.prepareIndex("twitter", "tweet", "1") -// .setSource(jsonBuilder() -// .startObject() -// .field("user", "kimchy") -// .field("postDate", new Date()) -// .field("message", "trying out Elasticsearch") -// .endObject() -// ) -// .get(); -// -// //fixme works in debug, not in prod -//// assertThat(writer.getList().size()).isEqualTo(1); -// -// -// } -// -// -// private static class PluginConfigurableNode extends Node { -// -// public PluginConfigurableNode(Settings settings, -// Collection> classpathPlugins) { -// super(InternalSettingsPreparer.prepareEnvironment(settings, null), classpathPlugins); -// } -// } -//} +public class ElasticsearchIntegrationTest { + // + // + // private static ListWriter writer = new ListWriter(); + // private static DDTracer tracer = new DDTracer(writer); + // private static final int HTTP_PORT = 9205; + // private static final String HTTP_TRANSPORT_PORT = "9300"; + // private static final String ES_WORKING_DIR = "target/es"; + // private static String clusterName = "elasticsearch"; + // private static Node node; + // + // + // @AfterClass + // public static void stopElasticsearch() throws Exception { + // node.close(); + // } + // + // @BeforeClass + // public static void warmup() throws NodeValidationException { + // + // + // //GlobalTracer.register(tracer); + // + // + // Settings settings = Settings.builder() + // .put("path.home", ES_WORKING_DIR) + // .put("path.data", ES_WORKING_DIR + "/data") + // .put("path.logs", ES_WORKING_DIR + "/logs") + // .put("transport.type", "netty4") + // .put("http.type", "netty4") + // .put("cluster.name", clusterName) + // .put("http.port", HTTP_PORT) + // .put("transport.tcp.port", HTTP_TRANSPORT_PORT) + // .put("network.host", "0.0.0.0") + // .build(); + // Collection plugins = Collections.singletonList(Netty4Plugin.class); + // node = new PluginConfigurableNode(settings, plugins); + // node.start(); + // } + // + // + // @Test + // public void testTransportClient() throws IOException { + // + // + // Settings settings = Settings.builder() + // .put("cluster.name", clusterName).build(); + // + // TransportClient client = new PreBuiltTransportClient(settings) + // .addTransportAddress(new InetSocketTransportAddress(Inet4Address.getByName("localhost"), Integer.parseInt(HTTP_TRANSPORT_PORT))); + // + // IndexResponse response = client.prepareIndex("twitter", "tweet", "1") + // .setSource(jsonBuilder() + // .startObject() + // .field("user", "kimchy") + // .field("postDate", new Date()) + // .field("message", "trying out Elasticsearch") + // .endObject() + // ) + // .get(); + // + // //fixme works in debug, not in prod + //// assertThat(writer.getList().size()).isEqualTo(1); + // + // + // } + // + // + // private static class PluginConfigurableNode extends Node { + // + // public PluginConfigurableNode(Settings settings, + // Collection> classpathPlugins) { + // super(InternalSettingsPreparer.prepareEnvironment(settings, null), classpathPlugins); + // } + // } +} diff --git a/dd-java-agent/README.md b/dd-java-agent/README.md index 17c9ce4e57..8ddfe06ad1 100644 --- a/dd-java-agent/README.md +++ b/dd-java-agent/README.md @@ -9,7 +9,7 @@ Tracing instrumentation can be done in 2 ways: - Automatically over a set of [supported Web servers, frameworks or database drivers](#instrumented-frameworks) - By using the [`@Trace` annotation](#custom-instrumentations) -:heavy_exclamation_mark: **Warning:** This library is currently in Alpha. This means that even though we rigorously tested instrumentations you may experience strange behaviors depending on your running environment. Be sure to test thoroughly on a staging environment before releasing to production. For any help please contact [tracehelp@datadoghq.com](mailto:tracehelp@datadoghq.com). +:heavy_exclamation_mark: **Warning:** This library is currently in Alpha. This means that even though we rigorously tested instrumentations you may experience strange behaviors depending on your running environment. Be sure to test thoroughly on a staging environment before releasing to production. For any help please contact [tracehelp@datadoghq.com](mailto:tracehelp@datadoghq.com) or reach out in the datadoghq slack channel: #apm-java. ## Quick start @@ -17,7 +17,7 @@ Tracing instrumentation can be done in 2 ways: The Java instrumentation library works in collaboration with a local agent that transmits the traces to Datadog. To install it with tracing please follow these steps: -- Run the latest [Datadog Agent](https://app.datadoghq.com/account/settings#agent) (version 5.11.0 or above) +- Run the latest [Datadog Agent](https://app.datadoghq.com/account/settings#agent) (version 5.11.0 or above, or [special instructions for Mac OS X](https://github.com/DataDog/datadog-trace-agent#run-on-osx)) - [Enable APM in the Datadog Agent configuration file](https://app.datadoghq.com/apm/docs/tutorials/configuration) `/etc/dd-agent/datadog.conf`. ``` @@ -29,7 +29,7 @@ apm_enabled: true ### 2. Instrument your application -To instrument your project or your servers you simply have to declare the provided `jar` file in your JVM arguments as a valid `-javaagent:`. +To dynamically apply instrumentation you simply have to declare the provided `jar` file in your JVM arguments as a valid `-javaagent:`. - So first download the `jar` file from the main repository. @@ -38,13 +38,14 @@ To instrument your project or your servers you simply have to declare the provid curl -OL http://central.maven.org/maven2/com/datadoghq/dd-java-agent/{version}/dd-java-agent-{version}.jar ``` -- Then add the following JVM argument when launching your application (in IDE, using Maven run or simply in collaboration with the `>java -jar` command): +- Then add the following JVM argument when launching your application (in your IDE, your maven or gradle application script, or your `java -jar` command): ``` -javaagent:/path/to/the/dd-java-agent-{version}.jar ``` That's it! If you did this properly the agent was executed at pre-main, had detected and instrumented the supported libraries and custom traces. You should then see traces on [Datadog APM](https://app.datadoghq.com/apm/search). +For troubleshooting, look for the `trace-agent.log` along side the other [agent logs](https://help.datadoghq.com/hc/en-us/articles/203037159-Log-Locations). ## Configuration @@ -80,21 +81,22 @@ sampler: # enableCustomAnnotationTracingOver: ["io","org","com"] # Disable some instrumentations -# disabledInstrumentations: ["apache http", "mongo", "jetty", "tomcat", ...] +# disabledInstrumentations: ["opentracing-apache-httpclient", "opentracing-mongo-driver", "opentracing-web-servlet-filter"] ``` ## Instrumented frameworks -When attached to an application the `dd-java-agent` automatically instruments the following set of frameworks & servers: +When attached to an application the `dd-java-agent` dynamically applies the following opentracing-contrib instrumentation for the following set of frameworks & servers, though additional configuration may be required ([JDBC](#jdbc-instrumentation)): ### Frameworks -| FWK | Versions | Comments | +| Framework | Versions | Comments | | ------------- |:-------------:| ----- | -| OkHTTP | 3.x | HTTP client calls with [cross-process](http://opentracing.io/documentation/pages/api/cross-process-tracing.html) headers | -| Apache HTTP Client | 4.3 + |HTTP client calls with [cross-process](http://opentracing.io/documentation/pages/api/cross-process-tracing.html) headers| -| AWS SDK | 1.11.119+ | Trace all client calls to any AWS service | -| Web Servlet Filters| Depending on server | See [Servers](#servers) section | +| [OkHTTP](https://github.com/opentracing-contrib/java-okhttp) | 3.x | HTTP client calls with [cross-process](http://opentracing.io/documentation/pages/api/cross-process-tracing.html) headers | +| [Apache HTTP Client](https://github.com/opentracing-contrib/java-apache-httpclient) | 4.3 + | HTTP client calls with [cross-process](http://opentracing.io/documentation/pages/api/cross-process-tracing.html) headers| +| [AWS SDK](https://github.com/opentracing-contrib/java-aws-sdk) | 1.11.119+ | Trace all client calls to any AWS service | +| [Web Servlet Filters](https://github.com/opentracing-contrib/java-web-servlet-filter) | Depending on server | See [Servers](#servers) section | +| [JMS 2](https://github.com/opentracing-contrib/java-jms) | 2.x | Trace calls to message brokers, but distributed trace propagation not yet implemented | ### Servers @@ -110,9 +112,9 @@ Modern web application frameworks such as Dropwizard or Spring Boot are automati | ------------- |:-------------:| ----- | | Spring JDBC| 4.x | Please check the following [JDBC instrumentation](#jdbc-instrumentation) section | | Hibernate| 5.x | Please check the following [JDBC instrumentation](#jdbc-instrumentation) section | -| MongoDB | 3.x | Intercepts all the calls from the MongoDB client | -| Cassandra | 3.2.x | Intercepts all the calls from the Cassandra client | -| Elasticsearch | 5.4.x | Intercepts all the calls from the ES Transport client | +| [MongoDB](https://github.com/opentracing-contrib/java-mongo-driver) | 3.x | Intercepts all the calls from the MongoDB client | +| [Cassandra](https://github.com/opentracing-contrib/java-cassandra-driver) | 3.2.x | Intercepts all the calls from the Cassandra client | +| [Elasticsearch](https://github.com/opentracing-contrib/java-elasticsearch-client) | 5.4.x | Intercepts all the calls from the ES Transport client | #### JDBC instrumentation @@ -120,7 +122,7 @@ By enabling the JDBC instrumentation you'll intercept all the client calls to t But unfortunately this can not be done entirely automatically today. To enable tracing please follow the instructions provided on the [java-jdbc opentracing contrib project](https://github.com/opentracing-contrib/java-jdbc#usage). -We also provide an [example project with Spring Boot & MySQL](web application frameworks). +We also provide an [example project](../dd-trace-examples/spring-boot-jdbc) with Spring Boot & H2. ### Disabling instrumentations @@ -130,14 +132,14 @@ If for some reason you need to disable an instrumentation you should uncomment t ... # Disable a few instrumentations -disabledInstrumentations: ["apache http", "mongo", "tomcat"] +disabledInstrumentations: ["opentracing-apache-httpclient", "opentracing-mongo-driver", "opentracing-web-servlet-filter"] -... ``` +The list of values that can be disabled are the top level keys found [here](src/main/resources/dd-trace-supported-framework.yaml) ### -## Custom instrumentations +## Custom instrumentation ### The `@Trace` annotation @@ -172,21 +174,25 @@ public void myMethod() throws InterruptedException{ {version} ``` +or +```gradle +compile group: 'com.datadoghq', name: 'dd-trace-annotations', version: {version} +``` -- Enable custom tracing by adding in the `dd-trace.yaml` config file the packages you would like to scan as follow `enableCustomAnnotationTracingOver: ["io","org","com"]`. +- Enable custom tracing in the `dd-trace.yaml` config file by setting the packages you would like to scan as follows `enableCustomAnnotationTracingOver: ["io","org","com"]`. If you want to see custom tracing in action please run the [Dropwizard example](https://github.com/DataDog/dd-trace-java/blob/dev/dd-trace-examples/dropwizard-mongo-client/). ## Other useful resources -Before instrumenting your own project you might want to run the provided examples: +Before instrumenting your own project you might want to review the provided examples: - [Dropwizard/MongoDB & Cross process client calls](https://github.com/DataDog/dd-trace-java/blob/dev/dd-trace-examples/dropwizard-mongo-client/) -- [Springboot & MySQL over JDBC](https://github.com/DataDog/dd-trace-java/tree/dev/dd-trace-examples/spring-boot-jdbc) +- [Springboot & H2 over JDBC](https://github.com/DataDog/dd-trace-java/tree/dev/dd-trace-examples/spring-boot-jdbc) Other links that you might want to read: -- Install on [Docker](https://app.datadoghq.com/apm/docs/tutorials/docker) +- Improve your APM experience for apps running on docker by enabling the [Docker Agent](https://app.datadoghq.com/apm/docs/tutorials/docker) - Datadog's APM [Terminology](https://app.datadoghq.com/apm/docs/tutorials/terminology) - [FAQ](https://app.datadoghq.com/apm/docs/tutorials/faq) diff --git a/dd-java-agent/src/main/java/com/datadoghq/trace/agent/integration/DDAgentTracingHelper.java b/dd-java-agent/src/main/java/com/datadoghq/trace/agent/integration/DDAgentTracingHelper.java index 2c36c302b8..7f1beb91fc 100644 --- a/dd-java-agent/src/main/java/com/datadoghq/trace/agent/integration/DDAgentTracingHelper.java +++ b/dd-java-agent/src/main/java/com/datadoghq/trace/agent/integration/DDAgentTracingHelper.java @@ -8,7 +8,7 @@ import java.util.logging.Logger; import org.jboss.byteman.rule.Rule; /** - * This class provides helpfull stuff in order to easy patch object using Byteman rules + * This class provides helpful stuff in order to easy patch object using Byteman rules * * @param The type of the object to patch */ diff --git a/dd-trace-examples/README.md b/dd-trace-examples/README.md index 2254187c02..872a3592fe 100644 --- a/dd-trace-examples/README.md +++ b/dd-trace-examples/README.md @@ -1,7 +1,7 @@ ## Datadog Java Tracer examples The goal of this repository is to offer you some examples about how to instrument your code -using the Opentracing API and the DD Tracer. +using the OpenTracing API and the DD Tracer. ![](https://datadog-live.imgix.net/img/datadog_logo_share_tt.png) diff --git a/dd-trace-examples/async-tracing/README.md b/dd-trace-examples/async-tracing/README.md index 75620e1319..b546917f37 100644 --- a/dd-trace-examples/async-tracing/README.md +++ b/dd-trace-examples/async-tracing/README.md @@ -1,7 +1,7 @@ -## Opentracing Javaagent +## OpenTracing Javaagent ### Purpose -The Opentracing Java Agent contribution is designed to inject code directly to the JVM. +The OpenTracing Java Agent contribution is designed to inject code directly to the JVM. It provides to developers a way to instrument their code, without modifying it. The Java Agent is a compiled Jar and it is added to the JVM using the `-javaagent` option. @@ -10,7 +10,7 @@ a set of rules for instrumenting the code through a collection of `otarules.btm` The contrib is basically able to serve 2 goals: - Instrumenting custom or legacy code without modifying it (extremely verbose and painful) -- Inject the others Opentracing contribution in your app (Spring Boot, JDBC wrapper, Jax-Rs, etc. ) +- Inject the others OpenTracing contribution in your app (Spring Boot, JDBC wrapper, Jax-Rs, etc. ) and configure them on-fly. ### Run the demo @@ -39,7 +39,7 @@ First add the contrib to the dependencies. You can find them here: https://github.com/opentracing-contrib ```xml - + io.opentracing.contrib opentracing-agent-rules-java-net @@ -97,5 +97,3 @@ You have to add all rules necessary to instrument your code as you want. This is why (almost) nobody uses the agent in that way. Similarly to the previous example, the tracer is initialised through the yaml config file. - - \ No newline at end of file diff --git a/dd-trace/README.md b/dd-trace/README.md index dcdcd292f7..3dc90b6c9e 100644 --- a/dd-trace/README.md +++ b/dd-trace/README.md @@ -1,12 +1,12 @@ -# Datadog Opentracing Tracer +# Datadog OpenTracing Tracer ## Motivations -The Datadog Tracer is an [Opentracing](http://opentracing.io/) compatible tracer. It provides all resources needed to instrument your code +The Datadog Tracer is an [OpenTracing](http://opentracing.io/) compatible tracer. It provides all resources needed to instrument your code and report each operation and each trace directly to a Datadog APM platform. -Opentracing uses the concept of the **span**. A span is **timed operation** representing a bunch of work executed. +OpenTracing uses the concept of the **span**. A span is **timed operation** representing a bunch of work executed. Spans can **be linked together**. And a **trace** is a collection of spans, related to the same top action/operation. Let's see an example. @@ -25,7 +25,7 @@ TRACE: |----------------------------------------SPAN 4 (Child of 2)..(end) - 50 ms ```` -Opentracing provides a way for measuring the time consumed for each operation. +OpenTracing provides a way for measuring the time consumed for each operation. As just described, the tracer produces a trace composed of 4 spans, each representing a specific action: 1. Span1 is the time from doing the request to getting the response. @@ -34,7 +34,7 @@ on the DB. 3. Span3, a Span1' grandchild, represents the DB time used to retrieve the data 4. Span4 is a child of Span2 and followed Span3. It represents a business/legacy operation. -This is a very simple example of how works [Opentracing](http://opentracing.io/). +This is a very simple example of how works [OpenTracing](http://opentracing.io/). To dig deeper, read the full documentation: http://opentracing.io/ @@ -44,13 +44,13 @@ In order to start to instrument your application, you need to: 1. [Configure the Datadog Tracer](#config) 2. Choose one of the 3 ways to instrument an application: - 1. [Use the autotracing agent for supported frawemorks](#framework) - 2. [Use the Opentracing API](#api) + 1. [Use dd-java-agent for supported frawemorks](#framework) + 2. [Use the OpenTracing API in your code](#api) 3. [Use annotations](#annotation) ### Datadog Tracer configuration -The DDTracer is auto-configured using this YAML file. +The DDTracer is configured using a YAML file named `dd-trace.yaml` following the structure below. By default, the DDTracer tries to reach a local Datadog Agent, but you can change the settings and use a different location. In order to do that, please, refer you to the latest configuration: [dd-trace.yaml](src/main/resources/dd-trace.yaml) @@ -85,7 +85,7 @@ sampler: ### Use the Datadog Java agent for well-known framework Datadog uses instrumentation contributed by [the community](https://github.com/opentracing-contrib) to instrument many frameworks: -SpringBoot, JDBC, Mongo, JMS, Tomcat, etc. By using the Datadog Java agent, you just need to follow few steps in order to get traces. +SpringBoot, JDBC, Mongo, JMS, Tomcat, etc. By using [dd-java-agent](../dd-java-agent), you just need to follow few steps in order to get traces. Get the latest version of the Datadog Java agent (Do not forget to replace the version `${version}` by the appropriate one). @@ -107,9 +107,9 @@ You can choose which framework you want to instrument, or sending traces to a re Check the dedicated project for the full documentation: [dd-java-agent](../dd-java-agent) -### Custom instrumentations using Opentracing API +### Custom instrumentations using OpenTracing API -If you want to add custom instrumenting to your code, you have to use the Opentracing API. +If you want to add custom instrumenting to your code, you have to use the OpenTracing API. The official documentation can be found right here: [](https://github.com/opentracing/opentracing-java). Let's look at a simple example. @@ -117,7 +117,6 @@ Let's look at a simple example. ```java class InstrumentedClass { - void method0() { // Retrieve the tracer using the resolver provided @@ -154,6 +153,7 @@ public class Application { Tracer tracer = DDTracerFactory.createFromConfigurationFile(); io.opentracing.util.GlobalTracer.register(tracer); + // OR // Init the tracer from the API Writer writer = new com.datadoghq.trace.writer.DDAgentWriter(); Sampler sampler = new com.datadoghq.trace.sampling.AllSampler(); @@ -165,36 +165,38 @@ public class Application { } ``` -The factory looks for a `dd-trace.yaml` file in the classpath. +`DDTracerFactory` looks for a `dd-trace.yaml` file in the classpath. Finally, do not forget to add the corresponding dependencies to your project. - -``` - +Maven: +```xml + io.opentracing opentracing-api ${opentracing.version} - + com.datadoghq dd-trace ${dd-trace-java.version} - - compile group: 'io.opentracing', name: 'opentracing-api', version: '${opentracing.version}' - compile group: 'com.datadoghq', name: 'dd-trace', version: '${dd-trace-java.version}' ``` +Gradle: +```groovy + compile group: 'io.opentracing', name: 'opentracing-api', version: "${opentracing.version}" + compile group: 'com.datadoghq', name: 'dd-trace', version: "${dd-trace-java.version}" +``` -### Custom instrumentations using Annotation +### Adding Trace annotations to your methods -Datadog provides a third way to instrument your code: annotations. -The following example is the same as above. Just add `@Trace` to the methods you want to instrument. +An easy way to improve visibility to your application is by adding the `@Trace` annotation on the methods you want to instrument. +This is equivelent to the `method0` example from the [api](#api) section. ```java class InstrumentedClass { @@ -219,35 +221,34 @@ class InstrumentedClass { } ``` -In order to use annotations, the only required dependency is that package. -``` +In order to use annotations, the only required dependency is `dd-trace-annotations`. +Maven: +```xml com.datadoghq dd-trace-annotations ${dd-trace-java.version} - - compile group: 'com.datadoghq', name: 'dd-trace-annotations', version: '${dd-trace-java.version}' ``` -The annotations are resolved at the runtime by the Datadog Java agent. If you want to use the annotations, -so you must run the Datadog Java Agent. +Gradle: +```groovy + compile group: 'com.datadoghq', name: 'dd-trace-annotations', version: "${dd-trace-java.version}" +``` +**The annotations are resolved at the runtime by the Datadog Java agent. If you want to use the annotations, +so you must run the Datadog Java Agent.** To run the agent, please refer to the Datadog Java agent documentation: [dd-java-agent](../dd-java-agent) - ## Other useful resources -Before instrumenting your own project you might want to run the provided examples: +Before instrumenting your own project you might want to review the provided examples: - [Dropwizard/MongoDB & Cross process client calls](https://github.com/DataDog/dd-trace-java/blob/dev/dd-trace-examples/dropwizard-mongo-client/) -- [Springboot & MySQL over JDBC](https://github.com/DataDog/dd-trace-java/tree/dev/dd-trace-examples/spring-boot-jdbc) +- [Springboot & H2 over JDBC](https://github.com/DataDog/dd-trace-java/tree/dev/dd-trace-examples/spring-boot-jdbc) Other links that you might want to read: -- Install on [Docker](https://app.datadoghq.com/apm/docs/tutorials/docker) +- Improve your APM experience for apps running on docker by enabling the [Docker Agent](https://app.datadoghq.com/apm/docs/tutorials/docker) - Datadog's APM [Terminology](https://app.datadoghq.com/apm/docs/tutorials/terminology) - [FAQ](https://app.datadoghq.com/apm/docs/tutorials/faq) - - -And for any questions, feedback, feel free to send us an email: support@datadoghq.com \ No newline at end of file diff --git a/dd-trace/docs/opentracing-api.md b/dd-trace/docs/opentracing-api.md index 338f6b49a3..38f075e33c 100644 --- a/dd-trace/docs/opentracing-api.md +++ b/dd-trace/docs/opentracing-api.md @@ -1,10 +1,10 @@ -# Opentracing API +# OpenTracing API The Opentraction group offers an API to instrument your code. This document is a kind of a "Quick start for the" official specifications: https://github.com/opentracing/specification -There are several concepts expose by the Opentracing API: +There are several concepts expose by the OpenTracing API: * The core API used for instrumenting the code * The tracer implementations, in charge of generating physically the traces. For instance the Datadog Java Tracer generates @@ -12,7 +12,7 @@ traces that can be consumed by the Datadog agent. * The Asynchronous API to help developers managing their spans and traces in a concurrency context. -## Opentracing Core API +## OpenTracing Core API Official documentation link: [Opentracting Tracer specification](https://github.com/opentracing/specification/blob/master/specification.md#tracer) @@ -34,7 +34,7 @@ to send the traces to a logger or directly to a running Datadog agent. Tracer tracer = new DDTracer(); ``` -Once a tracer is instantiated, you can use it to create and manage span. Opentracing defines a SpanBuilder accessible through +Once a tracer is instantiated, you can use it to create and manage span. OpenTracing defines a SpanBuilder accessible through the method `buildSpan(String operationName)` to serve this purpose. @@ -77,7 +77,7 @@ You can manipulate them at any time and add extra information using the tags. Tags are local to the span. So, no tags will be inherit from the parent. In order to propagate meta accross all spans of a trace, use the `baggageItems` (see right after). -Opentracing Tags are standardized meta and allow developers to add more value to the span. +OpenTracing Tags are standardized meta and allow developers to add more value to the span. ```java // Create a span, but do not promoting it as the active span @@ -93,7 +93,7 @@ Opentracing Tags are standardized meta and allow developers to add more value to Tags.HTTP_STATUS.setTag(valuableSpan, 200); ``` -All standardized tags can be consulted there: [Opentracing Semantic specification](https://github.com/opentracing/specification/blob/master/semantic_conventions.md) +All standardized tags can be consulted there: [OpenTracing Semantic specification](https://github.com/opentracing/specification/blob/master/semantic_conventions.md) So, tags are local to the span. If you want set for meta for a trace, you have to use `baggabeItems` instead. Baggage are very similar to the tags, but they have a powerful capabilities: @@ -106,5 +106,5 @@ Baggage are very similar to the tags, but they have a powerful capabilities: ``` -## Opentracing Asynchronous API -see WIP: https://github.com/opentracing/specification/issues/23 \ No newline at end of file +## OpenTracing Asynchronous API +see WIP: https://github.com/opentracing/specification/issues/23 From 6c29e2f658ab69c003e21d4def41a8589e4e2cd0 Mon Sep 17 00:00:00 2001 From: Tyler Benson Date: Wed, 12 Jul 2017 16:28:10 -0700 Subject: [PATCH 2/7] Add more to the opentracing quick start guide --- dd-trace/README.md | 4 +- dd-trace/docs/opentracing-api.md | 142 +++++++++++++++++++------------ 2 files changed, 91 insertions(+), 55 deletions(-) diff --git a/dd-trace/README.md b/dd-trace/README.md index 3dc90b6c9e..2c5c1d90b2 100644 --- a/dd-trace/README.md +++ b/dd-trace/README.md @@ -109,8 +109,8 @@ Check the dedicated project for the full documentation: [dd-java-agent](../dd-ja ### Custom instrumentations using OpenTracing API -If you want to add custom instrumenting to your code, you have to use the OpenTracing API. -The official documentation can be found right here: [](https://github.com/opentracing/opentracing-java). +Rather than referencing classes directly from `dd-trace` (other than registering `DDTracer`), we strongly suggest using the [OpenTracing API](https://github.com/opentracing/opentracing-java). +[Additional documentation on the api](docs/opentracing-api.md) is also available. Let's look at a simple example. diff --git a/dd-trace/docs/opentracing-api.md b/dd-trace/docs/opentracing-api.md index 38f075e33c..3fdbed59e6 100644 --- a/dd-trace/docs/opentracing-api.md +++ b/dd-trace/docs/opentracing-api.md @@ -2,109 +2,145 @@ The Opentraction group offers an API to instrument your code. -This document is a kind of a "Quick start for the" official specifications: https://github.com/opentracing/specification +This document is a kind of a "quick start" for the official specification: https://github.com/opentracing/specification -There are several concepts expose by the OpenTracing API: +There are several concepts exposed by the OpenTracing API: * The core API used for instrumenting the code -* The tracer implementations, in charge of generating physically the traces. For instance the Datadog Java Tracer generates -traces that can be consumed by the Datadog agent. -* The Asynchronous API to help developers managing their spans and traces in a concurrency context. +* The tracer implementations are in charge of capturing and reporting the traces. For instance `dd-trace` generates and reports traces to the Datadog trace agent. +* In-process trace propagation for trace consistency in a concurrent/asynchronous request context. +* Distributed trace propagation for when receiving a request and making external calls. ## OpenTracing Core API -Official documentation link: [Opentracting Tracer specification](https://github.com/opentracing/specification/blob/master/specification.md#tracer) +Official documentation link: [Opentracting Tracer specification](https://github.com/opentracing/specification/blob/master/specification.md) The core API exposes 3 main objects: -* A **Tracer** -* A **Span** -* A collection of **Tags** +* A [Tracer](https://github.com/opentracing/specification/blob/master/specification.md#tracer) +* A [Span](https://github.com/opentracing/specification/blob/master/specification.md#span) +* A collection of **Tags** associated with a Span +### Tracers -The tracer is in charge of instantiate new spans, and sending them to the appropriate sink. +The tracer is in charge of instantiating new spans for a given context, and sending them to the appropriate sink when complete. -The tracer instantiate depends of the implementation you chose. For instance, the Datadog Java Tracer allows you +The tracer instantiation depends of the implementation you chose. For instance, `dd-trace` allows you to send the traces to a logger or directly to a running Datadog agent. ```java - // Initialize the Datadog Java Tracer - Tracer tracer = new DDTracer(); + // Initialize the Datadog Java Tracer to write traces to the log: + Tracer tracer = new DDTracer(); ``` -Once a tracer is instantiated, you can use it to create and manage span. OpenTracing defines a SpanBuilder accessible through -the method `buildSpan(String operationName)` to serve this purpose. - +After a tracer is created, you will usually want to register it with the `GlobalTracer` +to make it accessible all OpenTracing instrumentation in your JVM. ```java - // Create a new Span with the operation name "componentTracking" - Span current = tracer.buildSpan("componentTracking").startActive(); + io.opentracing.util.GlobalTracer.register(tracer); ``` -This example creates a simple span referenced "componentTracking". The `startActive()` method starts a new span and set it -as the active. This means that all new spans created after will be related to this one as children. If a span is already -the active one, the new span will replace it. +### Spans +Once a tracer is instantiated, you can use it to create and manage span. OpenTracing defines a SpanBuilder +accessible through the method `buildSpan(String operationName)` to serve this purpose. + +```java + // Create a new Span with the operation name "componentTracking" + ActiveSpan current = tracer.buildSpan("componentTracking").startActive(); +``` + +This example creates a simple span referenced "componentTracking". The `startActive()` method starts a new span and sets it +as the active span. This means that any new span created going forward on the same thread will reference this as its' parent. +If another span is already active, the new span will replace it. **A collection of related spans is called a trace.** -But, sometimes you need to create a span without promoting it as the active. If you want to do that, use the `startManual()` +Sometimes you need to create a span without promoting it as the active. If you want to do that, use the `startManual()` method instead. - ```java - // Create a span, but do not promoting it as the active span - Span anotherSpan = tracer.buildSpan("componentTracking").startManual(); + // Create a span, but do not promoting it as the active span + Span anotherSpan = tracer.buildSpan("componentTracking").startManual(); ``` - -Typically, span creations are made in the begging of the methods you want to trace. +Typically, span creations are made in the beginning of the methods you want to trace. And of course, you need to finish/close the span in order to get the operation duration. This is achieving using the `finish` method. ```java - // Finishing the tracing operation - current.finish() + // Finishing the tracing operation + current.finish() ``` -**Be careful!!** You have to be sure that all children spans are finished/closed before calling the method on the root span. -If you don't do this, you may face to span incomplete issues or some traces/spans will not be reported by the tracer. +**Be careful!!** All children spans must be finished/closed before finishing the root span. +If child spans are unfinished when the parent attempts to finish, the span will remain incomplete and risk being unreported. Now, you are able to create, start and stop very simple spans. -You can manipulate them at any time and add extra information using the tags. -Tags are local to the span. So, no tags will be inherit from the parent. In order to propagate meta accross all spans of a -trace, use the `baggageItems` (see right after). +You can manipulate them at any time and add contextual information using tags. -OpenTracing Tags are standardized meta and allow developers to add more value to the span. +### Tags + +Tags are local to each span and no tags will be inherited from the parent. Information relevant to all spans in a trace +should be stored as [baggage](#baggage). + +OpenTracing defines a [standard set of tags](https://github.com/opentracing/specification/blob/master/semantic_conventions.md#standard-span-tags-and-log-fields) and should be used appropriately. Custom tags can also be defined as needed. ```java - // Create a span, but do not promoting it as the active span - Span valuableSpan = tracer. - buildSpan("componentTracking") - .withTag("custom-meta", "some-useful-value") - .withTag(Tags.COMPONENT, "my-component-mysql") - .startActive(); + // Create a span and set it as the active span + ActiveSpan valuableSpan = tracer. + buildSpan("componentTracking") + .withTag("custom-meta", "some-useful-value") + .withTag(Tags.COMPONENT, "my-component-mysql") + .startActive(); - // Somewhere further in the code - Tags.HTTP_URL.setTag(valuableSpan, "https://my-endpoint/resource/item"); - Tags.HTTP_STATUS.setTag(valuableSpan, 200); + // Somewhere further in the code + Tags.HTTP_URL.setTag(valuableSpan, "https://my-endpoint/resource/item"); + Tags.HTTP_STATUS.setTag(valuableSpan, 200); ``` -All standardized tags can be consulted there: [OpenTracing Semantic specification](https://github.com/opentracing/specification/blob/master/semantic_conventions.md) +### Baggage -So, tags are local to the span. If you want set for meta for a trace, you have to use `baggabeItems` instead. -Baggage are very similar to the tags, but they have a powerful capabilities: -* A baggage is attached to all spans of a trace. -* A baggage is propagated outside the trace context via Http or Tcp protocols (depends of the tracer implementation). +Information relevant for the entire trace is stored as baggage. +Baggage is very similar to tags, but has important distinctions. Baggage is: +* Associated with all spans for a trace. +* Propagated outside the trace context via HTTP or Messaging protocols (depends of the tracer implementation). ```java - // Like tags, you can add baggage item to the span - valuableSpan.setBaggageItem("username", "@gpolaert"); + // Like tags, you can add baggage item to the span + valuableSpan.setBaggageItem("username", "modernmajorgeneral"); ``` - ## OpenTracing Asynchronous API -see WIP: https://github.com/opentracing/specification/issues/23 + +An `ActiveSpan` can generate a `Continuation` as a way of propagating traces from across a thread boundary. + +On the parent thread: +```java + Continuation spanContinuation = valuableSpan.capture(); + // pass the continuation onto a new thread +``` + +On a different thread: +```java + ActiveSpan valuableSpan = spanContinuation.activate(); + // span is now active on the new thread +``` + +## OpenTracing Cross Process Propagation + +Spans are associated across processes in a trace via the `Tracer.extract` and `Tracer.inject` methods. + +```java + // On the start of a new trace in an application, associate incoming request with existing traces. + SpanContext spanCtx = tracer.extract(Format.Builtin.HTTP_HEADERS, someTextMapInstance); + ActiveSpan currentSpan = tracer.buildSpan("componentTracking").asChildOf(spanCtx).startActive(); +``` + +```java + // When making an external call propagate the trace by injecting it into the carrier... + tracer.inject(currentSpan.context(), Format.Builtin.HTTP_HEADERS, someTextMapInstance); +``` From 04d0d3f8a2bc8141aa4d2375cf7ff03012482d7d Mon Sep 17 00:00:00 2001 From: Albert Wang Date: Thu, 13 Jul 2017 13:37:47 +0200 Subject: [PATCH 3/7] Update README.md --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 670e25c87e..816085c1bb 100644 --- a/README.md +++ b/README.md @@ -21,5 +21,5 @@ gather all traces in your [Datadog](https://app.datadoghq.com) account. ### Help or questions? -For any questions or feedback, feel free to send us an email: support@datadoghq.com -You can also ask for help in the datadoghq slack channel: #apm-java +For any questions or feedback, feel free to send us an email: tracehelp@datadoghq.com +You can also ask for help in the datadoghq slack channel: #apm-java. Signup at chat.datadoghq.com From 7d1035c7eb707d579f1a777a1431bf6f3806c37a Mon Sep 17 00:00:00 2001 From: Albert Wang Date: Thu, 13 Jul 2017 13:46:34 +0200 Subject: [PATCH 4/7] clarify span/trace docs --- dd-trace/README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/dd-trace/README.md b/dd-trace/README.md index 2c5c1d90b2..5cc8d5d17b 100644 --- a/dd-trace/README.md +++ b/dd-trace/README.md @@ -6,8 +6,8 @@ The Datadog Tracer is an [OpenTracing](http://opentracing.io/) compatible tracer and report each operation and each trace directly to a Datadog APM platform. -OpenTracing uses the concept of the **span**. A span is **timed operation** representing a bunch of work executed. -Spans can **be linked together**. And a **trace** is a collection of spans, related to the same top action/operation. +OpenTracing uses the concept of spans and traces. A **span** is timed operation representing a bunch of work executed. +Spans can be linked together. A **trace** is a collection of spans, related to the same top action/operation. Let's see an example. @@ -35,7 +35,7 @@ on the DB. 4. Span4 is a child of Span2 and followed Span3. It represents a business/legacy operation. This is a very simple example of how works [OpenTracing](http://opentracing.io/). -To dig deeper, read the full documentation: http://opentracing.io/ +Fore more information, see http://docs.datadoghq.com/tracing/terminology/ or http://opentracing.io/. ## How to instrument your application? From fc43738e81086c3a75de8e78894f1e2ad0adc9e8 Mon Sep 17 00:00:00 2001 From: Albert Wang Date: Thu, 13 Jul 2017 13:48:19 +0200 Subject: [PATCH 5/7] Update README.md --- dd-trace/README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/dd-trace/README.md b/dd-trace/README.md index 5cc8d5d17b..7c2ab0e163 100644 --- a/dd-trace/README.md +++ b/dd-trace/README.md @@ -31,8 +31,8 @@ As just described, the tracer produces a trace composed of 4 spans, each represe 1. Span1 is the time from doing the request to getting the response. 2. Span2 is the Span1's first child, representing the amount of time to understand the query, and perform the query on the DB. -3. Span3, a Span1' grandchild, represents the DB time used to retrieve the data -4. Span4 is a child of Span2 and followed Span3. It represents a business/legacy operation. +3. Span3 is Span1's grandchild, represents the DB time used to retrieve the data +4. Span4 is a child of Span2 and follows Span3. It represents a business/legacy operation. This is a very simple example of how works [OpenTracing](http://opentracing.io/). Fore more information, see http://docs.datadoghq.com/tracing/terminology/ or http://opentracing.io/. From a28e2209de0bab3ace8133e53aa50969f4bc295c Mon Sep 17 00:00:00 2001 From: Albert Wang Date: Thu, 13 Jul 2017 13:50:07 +0200 Subject: [PATCH 6/7] linkify chat --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 816085c1bb..f6a9dd0511 100644 --- a/README.md +++ b/README.md @@ -22,4 +22,4 @@ gather all traces in your [Datadog](https://app.datadoghq.com) account. ### Help or questions? For any questions or feedback, feel free to send us an email: tracehelp@datadoghq.com -You can also ask for help in the datadoghq slack channel: #apm-java. Signup at chat.datadoghq.com +You can also ask for help in the datadoghq slack channel: #apm-java. Signup at [chat.datadoghq.com](http://chat.datadoghq.com) From 2c4480b45a59ae1435c655f0e00a3110d8123539 Mon Sep 17 00:00:00 2001 From: Tyler Benson Date: Thu, 13 Jul 2017 08:21:09 -0700 Subject: [PATCH 7/7] Fix typo --- dd-trace/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dd-trace/README.md b/dd-trace/README.md index 7c2ab0e163..80c7cb2b85 100644 --- a/dd-trace/README.md +++ b/dd-trace/README.md @@ -35,7 +35,7 @@ on the DB. 4. Span4 is a child of Span2 and follows Span3. It represents a business/legacy operation. This is a very simple example of how works [OpenTracing](http://opentracing.io/). -Fore more information, see http://docs.datadoghq.com/tracing/terminology/ or http://opentracing.io/. +For more information, see http://docs.datadoghq.com/tracing/terminology/ or http://opentracing.io/. ## How to instrument your application?