At Instana, we believe that Observability should be as automated as possible. We often joke with each other about automagic. From the birth of Instana, we relentlessly invested in the creation of distributed tracing technology that you can deploy once and do not have to manually update, customize, redeploy, restart, or any of those other little “joys” of operating software.
The result of this philosophy is that Instana automatically traces hundreds upon hundreds of libraries and frameworks across several runtimes like JVM, Python, Node.js, .NET, Ruby and more. Something that automagic distributed trace instrumentation cannot do alone, though, is to glean business context from within the code. For example: you are providing an API used by multiple end users. Each end user belongs to an account. If your API is sending data about the account over, say, HTTP query parameters, Instana will collect it. But if you use authorization mechanisms like JWT, that data is not going to be sent to Instana and you cannot use it to filter your traces in Unbounded Analytics.
Traditionally, and Instana is no exception, observability vendors provide SDKs that allow you to add this business-relevant data to tracing. Indeed, Instana has a lot of SDKs available for every runtime we support.
Sometimes, however, adding an SDK and its respective code to your application is not an option. So, what we did is to enable you to add data to the Instana AutoTrace data without modifying one line of code of your applications. We call these new SDKs Configuration-based SDKs, and they are available for Java and .NET applications.
You can leverage the configuration-based SDKs by specifying which additional instrumentation to create using the Instana Agent configuration. Consider the following snippet of agent configuration:
com.instana.plugin.javatrace: instrumentation: sdk: targets: - match: type: class name: com.instana.java.sdk.BatchApplication method: batchArchiveProcesses span: name: ArchiveProcessRequests type: ENTRY stackDepth: 2 tags: - kind: constant name: endpoint value: archive - kind: argument name: batch.job index: 0
The configuration above tells the Instana agent to collect a new span, called ArchiveProcessRequests, every time the method com.instana.java.sdk.BatchApplication.batchArchiveProcesses is invoked in your applications. And not only a new span will be created, but it will also be annotated with the endpoint annotation, which will configure the Endpoint for this call in Application Perspectives, and use the value of the first argument (index: 0) of com.instana.java.sdk.BatchApplication.batchArchiveProcesses as the span tag batch.job, which will make the call look in Instana as a BATCH call. The stackDepth parameter allows you to specify how much of the stacktrace to collect, so that you can optimize the overhead. (Stacktraces are usually rather unimportant for BATCH calls, but your mileage may vary.) Finally, since the span declared is of type ENTRY, the instrumentation will create a new trace if none exists yet, which is very often the case for batch use-cases, in which each run should be captured by a different trace.
The documentation for the Configuration-based SDK for Java also shows an example of creating instrumentation for DATABASE calls, which can be really handy when your library of choice is not yet covered by Instana.
Programmatic SDKs ultimately rely on the assumption that you can change the code of the application that needs to expose more data. However, that is not always possible or desirable. The use-cases for configuration-based SDKs usually fall in one of the following categories:
- Cannot change the application’s code, like 3rd-party enterprise applications, a lot of them developed in Java and .NET over the past few decades, or the development teams writing those applications cannot do that (lack of capacity, other priorities, you name it).
- Cannot use a proprietary SDK in the codebase due to governance constraints or philosophical stances.
- Fill AutoTrace gaps because maybe Instana does not have just yet support for that database library you use, but you want to get visibility right away without having to write code with a programmatic SDK that has to be removed afterwards.
The configuration-based SDK is a cool new addition to the Instana toolkit, but it is something that should be deployed with the utmost care and deliberation.
Brittleness: The configuration-based SDK is brittle against changes in the application code. You may rename a class or a method, and all of a sudden the configuration no longer matches, and you silently lose tracing data you relied on. Whenever possible, we advise you to use programmatic SDKs, which are far more resilient against code changes and have more features to help you accomplish your goals.
“Just add one tag”: In terms of functionality gap, configuration-based SDKs do not yet allow you to just add a tag to an already-existing AutoTrace spans the way, say, the SpanSupport.annotate method of the Java Trace SDK allows you to. This is a relatively easy limitation to lift, and we have not done it yet because the use-case has not arisen more than a handful of times so far. If you do have one such use-case, let us know!
Trace continuity limitations: Additionally, configuration-based SDKs do not provide means of propagating trace context outside of your application, e.g., by adding the Instana HTTP headers to outgoing requests issues through an HTTP client Instana does not support yet. So, using just the configuration-based SDK, you cannot continue traces begun in other processes and, if you use the configuration-based SDK to trace some client your application uses, that other processes can continue the trace you create.
The settings used by the configuration-based SDKs are specified in the configuration.yaml files provided to the Instana agent. Something that not all Instana users are aware of, and that works like a charm with the configuration-based SDK, is that the Instana agent supports using multiple configuration.yaml files! So, you could divide your configuration-based SDK settings in different files, for example one per framework, and compositionally specify which settings should apply to which agents. Needless to say, it works like a charm with the GitOps support based right into the Instana agent, ensuring a nice, cloud-native user experience even in situations in which many different configuration-based SDK settings have to be configured.
- As the Product Manager for Distributed Tracing, I learned to live with the fact that some ecosystems are just so incredibly large and in constant expansion, that you simply cannot instrument everything people use. Nevertheless, I do sometimes have the distinct, uncomfortable impression that every day someone wakes up in the middle of the night, caught by an epiphany, and in a rapture creates a new library to do the very same thing other 50 do (like, HTTP clients on the JVM, or messaging libraries in Python) but juuuuuust a little differently. Naturally, on the very same day, one or more other someones find that to be the best idea since sliced bread and put it in production before their first coffee. ↑