Zero-Code Instrumentation of Java using OpenTelemetry

Instrument Java applications using Zero-Code OpenTelemetry with a Java agent to capture telemetry data without code changes.

Overview

Zero-code instrumentation in Java with OpenTelemetry uses a Java agent that attaches to any Java 8+ application (but certain instrumentations require Java 11+). This approach requires no changes to the application code itself, as the agent dynamically injects bytecode to capture telemetry from popular libraries and frameworks. This is particularly useful for capturing telemetry at the boundaries of an application, such as incoming requests, database calls, and outbound HTTP requests.

Download the Java Agent

Visit the OpenTelemetry Java Instrumentation Releases page and download the latest version of opentelemetry-javaagent.jar from the list of assets. This JAR file contains the necessary bytecode instrumentation libraries which will automatically instrument your application at runtime. Place the opentelemetry-javaagent.jar file within your project directory or a designated folder where your Java applications reside. This will make it convenient to reference the agent in your application startup commands in the next step.

Define the Agent and Properties

To use the Java agent, you can either modify your application’s startup command or define the agent and properties using environment variables:

Direct Command-Line Configuration

Modify your Java application’s startup command by adding the -javaagent parameter followed by the path to the downloaded opentelemetry-javaagent.jar file. This will load the agent along with your application. You should also define a service name for your application to help identifying your service in telemetry data. Add the -Dotel.service.name system property to specify this.

java -javaagent:/path/to/opentelemetry-javaagent.jar -Dotel.service.name=my-service -jar yourapp.jar

Replace my-service with a meaningful name for your application, replace /path/to/ with the path to the opentelemetry-javaagent.jar file you downloaded, and replace yourapp with the name of your application jar.

Note: Don’t run this command yet - there is more configuration required in the following sections.

(Alternative) Use Environment Variables

Instead of modifying your Java application’s startup command, you can define the Java agent and other configuration properties using environment variables. This is especially useful in containerized environments.

export JAVA_TOOL_OPTIONS="-javaagent:/path/to/opentelemetry-javaagent.jar"
export OTEL_SERVICE_NAME="my-service"

Replace my-service with a meaningful name for your application, replace /path/to/ with the path to the opentelemetry-javaagent.jar file you downloaded.

Configure Exporters

You configure OTLP exporters in your Java application to send telemetry (logs, traces, and metrics) to Edge Delta. The configuration differs depending on whether you’re sending to an Edge Pipeline (local Edge Delta agent) or a Cloud Pipeline (Edge Delta hosted infrastructure).

Edge Pipeline Configuration

Use this configuration when sending telemetry to an Edge Delta agent running in your environment. This is the typical setup for Kubernetes deployments or when the Edge Delta agent runs on the same host or network as your application.

What you configure:

ComponentConfiguration
Java applicationOTLP exporter endpoint pointing to Edge Delta agent
Edge Delta agentOTLP input node listening on the same port

Standard ports:

  • gRPC: Port 4317 (no path required)
  • HTTP: Port 4318 (paths /v1/traces, /v1/metrics, /v1/logs appended automatically)

Example: gRPC to Edge Pipeline (Kubernetes)

Configure the Java application to send to the Edge Delta agent service:

java -javaagent:/path/to/opentelemetry-javaagent.jar \
     -Dotel.service.name=my-service \
     -Dotel.traces.exporter=otlp \
     -Dotel.metrics.exporter=otlp \
     -Dotel.logs.exporter=otlp \
     -Dotel.exporter.otlp.protocol=grpc \
     -Dotel.exporter.otlp.endpoint=http://ed-data-supply-svc:4317 \
     -jar yourapp.jar

Or using environment variables:

export OTEL_SERVICE_NAME="my-service"
export OTEL_TRACES_EXPORTER=otlp
export OTEL_METRICS_EXPORTER=otlp
export OTEL_LOGS_EXPORTER=otlp
export OTEL_EXPORTER_OTLP_PROTOCOL=grpc
export OTEL_EXPORTER_OTLP_ENDPOINT=http://ed-data-supply-svc:4317

The Edge Delta agent configuration must include an OTLP input node listening on the same port:

- name: otlp_input
  type: otlp_input
  port: 4317
  protocol: grpc

Example: Same host (Linux VM)

When the Java application runs on the same host as the Edge Delta agent:

export OTEL_EXPORTER_OTLP_PROTOCOL=grpc
export OTEL_EXPORTER_OTLP_ENDPOINT=http://localhost:4317

See Ingest Data from an OTLP Source for detailed Edge Delta agent configuration.

Cloud Pipeline Configuration

Use this configuration when sending telemetry directly to an Edge Delta Cloud Pipeline without a local Edge Delta agent. Cloud Pipelines are hosted by Edge Delta and expose public endpoints for data ingestion.

Key differences from Edge Pipeline:

  • HTTPS required: Cloud Pipelines use TLS encryption on port 443
  • Protocol must be explicit: The Java agent defaults to http/protobuf, so you must set the protocol to match your endpoint type
  • No Edge Delta agent configuration: The Cloud Pipeline is pre-configured to receive OTLP data

What you configure:

ComponentConfiguration
Java applicationOTLP exporter with Cloud Pipeline endpoint, protocol, and TLS
Cloud PipelineAlready configured with OTLP input node (no changes needed)

Example: gRPC to Cloud Pipeline (Recommended)

java -javaagent:/path/to/opentelemetry-javaagent.jar \
     -Dotel.service.name=my-service \
     -Dotel.traces.exporter=otlp \
     -Dotel.metrics.exporter=otlp \
     -Dotel.logs.exporter=otlp \
     -Dotel.exporter.otlp.protocol=grpc \
     -Dotel.exporter.otlp.endpoint=https://pipeline-id-grpc-us-west2-cf.aws.edgedelta.com:443 \
     -jar yourapp.jar

Or using environment variables:

export OTEL_SERVICE_NAME="my-service"
export OTEL_TRACES_EXPORTER=otlp
export OTEL_METRICS_EXPORTER=otlp
export OTEL_LOGS_EXPORTER=otlp
export OTEL_EXPORTER_OTLP_PROTOCOL=grpc
export OTEL_EXPORTER_OTLP_ENDPOINT=https://pipeline-id-grpc-us-west2-cf.aws.edgedelta.com:443

Replace pipeline-id-grpc-us-west2-cf.aws.edgedelta.com with your Cloud Pipeline’s gRPC endpoint from the Pipeline Settings page.

Important: You must set -Dotel.exporter.otlp.protocol=grpc when using a gRPC endpoint. Without this setting, the Java agent defaults to HTTP protocol, which causes HTTP 415 (Unsupported Media Type) errors.

Example: HTTP to Cloud Pipeline

java -javaagent:/path/to/opentelemetry-javaagent.jar \
     -Dotel.service.name=my-service \
     -Dotel.traces.exporter=otlp \
     -Dotel.metrics.exporter=otlp \
     -Dotel.logs.exporter=otlp \
     -Dotel.exporter.otlp.protocol=http/protobuf \
     -Dotel.exporter.otlp.endpoint=https://pipeline-id-http-us-west2-cf.aws.edgedelta.com:443 \
     -jar yourapp.jar

Or using environment variables:

export OTEL_SERVICE_NAME="my-service"
export OTEL_TRACES_EXPORTER=otlp
export OTEL_METRICS_EXPORTER=otlp
export OTEL_LOGS_EXPORTER=otlp
export OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf
export OTEL_EXPORTER_OTLP_ENDPOINT=https://pipeline-id-http-us-west2-cf.aws.edgedelta.com:443

Replace pipeline-id-http-us-west2-cf.aws.edgedelta.com with your Cloud Pipeline’s HTTP endpoint from the Pipeline Settings page.

Finding your Cloud Pipeline endpoints:

  1. Navigate to Pipelines in the Edge Delta UI
  2. Select your Cloud Pipeline
  3. Click Settings
  4. Copy the GRPCS Endpoint or HTTPS Endpoint

Note: The UI displays endpoints with the grpcs:// prefix (for example, grpcs://pipeline-id-grpc-...). For the Java agent, replace grpcs:// with https:// when configuring your endpoint. The grpcs:// scheme is not recognized by the Java agent.

Configuration Summary

ScenarioProtocol SettingEndpoint FormatPort
Edge Pipeline (gRPC)grpchttp://host:43174317
Edge Pipeline (HTTP)http/protobufhttp://host:43184318
Cloud Pipeline (gRPC)grpchttps://...-grpc-...:443443
Cloud Pipeline (HTTP)http/protobufhttps://...-http-...:443443

See Cloud Pipelines for more information on Cloud Pipeline configuration and endpoints.

Explore Supported Libraries and Frameworks

The OpenTelemetry Java agent comes with built-in instrumentation for a wide array of popular libraries and frameworks. This automatic instrumentation can capture telemetry for operations such as HTTP requests, database activities, messaging systems, and more, without any need for code changes. See the available libraries and frameworks. Check that the versions of the libraries or frameworks you are using in your Java application are supported by the OpenTelemetry Java agent version you have downloaded.

Samplers

Optionally, you can include samplers in your instrumentation, for example to reduce trace data volume. You configure sampling by setting the otel.traces.sampler environment variable or JVM system property.

This example samples 10% of traces.

     -Dotel.traces.sampler=traceidratio \
     -Dotel.traces.sampler.arg=0.1 \

Or, using the Environment Variable approach:

export OTEL_TRACES_SAMPLER="traceidratio"
export OTEL_TRACES_SAMPLER_ARG="0.1"

ParentBased + Ratio-Based Sampling (Recommended for distributed tracing)

-Dotel.traces.sampler=parentbased_traceidratio
-Dotel.traces.sampler.arg=0.05  # 5% sample rate for new traces

Or, using the Environment Variable approach:

export OTEL_TRACES_SAMPLER="parentbased_traceidratio"
export OTEL_TRACES_SAMPLER_ARG="0.1"  # Sample 10% for new root traces

This ensures that:

  • New traces (requests with no parent trace) are sampled at a fixed rate.
  • Child spans (requests that belong to an existing trace) inherit their parent’s decision

Run and Verify Instrumentation

Run your Java application using the startup command configured with the OpenTelemetry Java agent.

Example: Edge Pipeline with gRPC

java -javaagent:/path/to/opentelemetry-javaagent.jar \
     -Dotel.service.name=my-service \
     -Dotel.traces.exporter=otlp \
     -Dotel.metrics.exporter=otlp \
     -Dotel.logs.exporter=otlp \
     -Dotel.exporter.otlp.protocol=grpc \
     -Dotel.exporter.otlp.endpoint=http://ed-data-supply-svc:4317 \
     -Dotel.traces.sampler=parentbased_traceidratio \
     -Dotel.traces.sampler.arg=0.05 \
     -jar yourapp.jar

Example: Cloud Pipeline with gRPC

java -javaagent:/path/to/opentelemetry-javaagent.jar \
     -Dotel.service.name=my-service \
     -Dotel.traces.exporter=otlp \
     -Dotel.metrics.exporter=otlp \
     -Dotel.logs.exporter=otlp \
     -Dotel.exporter.otlp.protocol=grpc \
     -Dotel.exporter.otlp.endpoint=https://pipeline-id-grpc-us-west2-cf.aws.edgedelta.com:443 \
     -Dotel.traces.sampler=parentbased_traceidratio \
     -Dotel.traces.sampler.arg=0.05 \
     -jar yourapp.jar

Environment Variables Approach

Alternatively, set environment variables and run the application:

java -jar yourapp.jar

Verify telemetry export:

  1. Check application logs and OpenTelemetry debug logs (enable with -Dotel.javaagent.debug=true) for export errors
  2. In Edge Delta, navigate to your pipeline and verify telemetry data is being received
  3. Look for your service name in traces, metrics, and logs
  4. Generate test traffic to confirm instrumentation is capturing expected operations