Warning

**Deprecation Notice**: The SDK will be deprecated in favor of the [OpenTelemetry SDK](https://opentelemetry.io/docs/languages/java/) and will no longer be supported after **June 30, 2026**. See the [end-of-life notice](https://coralogix.com/docs/user-guides/latest-updates/deprecations/logback-sdk/index.md) for migration details.

Here is a guide on how to send Java application logs to Coralogix by using [Logback](https://logback.qos.ch/) framework. The main focus of this guide is to integrate an [OpenTelemetry Java SDK](https://opentelemetry.io/docs/languages/java/) to Logback framework by implementing [opentelemetry-logback-appender-1.0](https://mvnrepository.com/artifact/io.opentelemetry.instrumentation/opentelemetry-logback-appender-1.0).

# Package dependencies setup

First step, you need to add these packages to your project:

- `ch.qos.logback:logback-classic`
- `ch.qos.logback:logback-core`
- `io.opentelemetry:opentelemetry-sdk`
- `io.opentelemetry:opentelemetry-exporter-otlp`
- `io.opentelemetry.instrumentation:opentelemetry-logback-appender-1.0`

Here is how your app's Gradle file can look like.

```text
dependencies {
  // Log4j
  implementation("ch.qos.logback:logback-classic:1.5.23")
  implementation("ch.qos.logback:logback-core:2.17.2")

  // OpenTelemetry SDK & OTLP exporter
  implementation("io.opentelemetry:opentelemetry-sdk")
  implementation("io.opentelemetry:opentelemetry-exporter-otlp")

  // OpenTelemetry log4j appender
  implementation("io.opentelemetry.instrumentation:opentelemetry-logback-appender-1.0")
}
```

Choose the https://ingress.\[[DOMAIN_VALUE]\] endpoint that corresponds to your Coralogix [domain](https://coralogix.com/docs/user-guides/account-management/account-settings/coralogix-domain/index.md) using the domain selector at the top of the page.

Maven:

```xml
    <properties>
        <maven.compiler.source>17</maven.compiler.source>
        <maven.compiler.target>17</maven.compiler.target>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <logback.version>1.5.23</logback.version>
        <opentelemetry.version>1.57.0</opentelemetry.version>
    </properties>

    <dependencies>
        <!-- Logback Core and Classic -->
        <dependency>
            <groupId>ch.qos.logback</groupId>
            <artifactId>logback-core</artifactId>
            <version>${logback.version}</version>
        </dependency>
        <dependency>
            <groupId>ch.qos.logback</groupId>
            <artifactId>logback-classic</artifactId>
            <version>${logback.version}</version>
        </dependency>

        <!-- OpenTelemetry SDK & OTLP exporter -->
        <dependency>
            <groupId>io.opentelemetry</groupId>
            <artifactId>opentelemetry-sdk</artifactId>
            <version>${opentelemetry.version}</version>
        </dependency>
        <dependency>
            <groupId>io.opentelemetry</groupId>
            <artifactId>opentelemetry-exporter-otlp</artifactId>
            <version>${opentelemetry.version}</version>
        </dependency>
        <dependency>
            <groupId>io.opentelemetry</groupId>
            <artifactId>opentelemetry-sdk-logs</artifactId>
            <version>${opentelemetry.version}</version>
        </dependency>

        <!-- OpenTelemetry Logback Appender -->
        <dependency>
            <groupId>io.opentelemetry.instrumentation</groupId>
            <artifactId>opentelemetry-logback-appender-1.0</artifactId>
            <version>2.23.0-alpha</version>
        </dependency>
    </dependencies>
```

Please make sure to update the packages to the latest version if you'll use this example for testing.

# Configure Logback

Here is how you configure Logback appender in `logback.xml` to send logs to OpenTelemetry endpoint.

```xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
    <appender name="console" class="ch.qos.logback.core.ConsoleAppender">
        <encoder>
            <pattern>
                %d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
            </pattern>
        </encoder>
    </appender>

    <appender name="OpenTelemetry"
        class="io.opentelemetry.instrumentation.logback.appender.v1_0.OpenTelemetryAppender">
        <captureExperimentalAttributes>false</captureExperimentalAttributes>
        <captureCodeAttributes>false</captureCodeAttributes>
        <captureMarkerAttribute>false</captureMarkerAttribute>
        <captureKeyValuePairAttributes>false</captureKeyValuePairAttributes>
        <captureLoggerContext>false</captureLoggerContext>
        <captureMdcAttributes>*</captureMdcAttributes>
    </appender>

    <root level="INFO">
        <appender-ref ref="console"/>
        <appender-ref ref="OpenTelemetry"/>
    </root>
</configuration>
```

# Application implementation

Finally, make the appender aware of your OpenTelemetry SDK instance as early as possible in your application's startup sequence:

```java
import io.opentelemetry.instrumentation.logback.appender.v1_0.OpenTelemetryAppender;
import io.opentelemetry.sdk.OpenTelemetrySdk;

public class Application {
    public static void main(String[] args) {
        // Initialize your OpenTelemetry SDK
        OpenTelemetrySdk openTelemetrySdk = initializeOpenTelemetry();

        // Install the OpenTelemetry appender
        OpenTelemetryAppender.install(openTelemetrySdk);

        // Your application code
        // ...
    }

    private static OpenTelemetrySdk initializeOpenTelemetry() {
        // Your OpenTelemetry SDK initialization code
        // ...
    }
}
```

Then, in your application code you can use Logback’s Mapped Diagnostic Context (MDC) to create loggers and create log messages. The following an example of creating a logger and logging a message.

```java
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.MDC;

public class YourService {
    private static final Logger logger = LoggerFactory.getLogger(YourService.class);

    public void processRequest(String requestId, String userId) {
        try {
            MDC.put("requestId", requestId);
            MDC.put("userId", userId);

            logger.info("Processing request");

            // Your business logic
            // ...

            logger.info("Request processed successfully");
        } finally {
            MDC.clear(); // Always clear MDC to prevent memory leaks
        }
    }
}
```

## Logging output

With OpenTelemetry SDK, we can send logs from the application either to local [OpenTelemetry Collector setup](https://coralogix.com/docs/opentelemetry/kubernetes-observability/kubernetes-observability-using-opentelemetry/index.md) or directly to Coralogix, using an OpenTelemetry endpoint.

### OpenTelemetry Collector

Once we configure the environment variable `OTEL_EXPORTER_OTLP_ENDPOINT`, setting it to the OpenTelemetry collector's endpoint, we should be able to see application logs coming to the target collector, from where we can also send logs to Coralogix.

### Coralogix OpenTelemetry endpoint

Once we configure the environment variables, setting it to the Coralogix OpenTelemetry endpoint with authentication header, application and subsystem name, we should be able to see application logs coming to Coralogix.

For setting up authentication, make sure to use the [Send-Your-Data API key](https://coralogix.com/docs/user-guides/account-management/api-keys/send-your-data-api-key/index.md).

```text
OTEL_EXPORTER_OTLP_ENDPOINT=https://ingress.[[DOMAIN_VALUE]]:443
OTEL_EXPORTER_OTLP_HEADERS="Authorization=Bearer send_your_data_key" \
OTEL_RESOURCE_ATTRIBUTES="cx.application.name=AppName, cx.subsystem.name=SubName"
```

## Additional resources

|                     |                                                                                             |
| ------------------- | ------------------------------------------------------------------------------------------- |
| Coralogix Endpoints | [Coralogix Endpoints](https://coralogix.com/docs/integrations/coralogix-endpoints/index.md) |

## Support

Need help? We love to assist our customers, simply reach out via our in-app chat, and we will walk you through, step by step.
