Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion README.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ readme's instructions.
=== Examples

// examples: START
Number of Examples: 66 (0 deprecated)
Number of Examples: 67 (0 deprecated)

[width="100%",cols="4,2,4",options="header"]
|===
Expand Down Expand Up @@ -168,6 +168,8 @@ Number of Examples: 66 (0 deprecated)
| link:salesforce/README.adoc[Salesforce] (salesforce) | SaaS | How to work with Salesforce contacts using REST endpoints and Streaming API

| link:twitter-salesforce/README.adoc[Twitter Salesforce] (twitter-salesforce) | SaaS | Twitter mentions is created as contacts in Salesforce

| link:observability-services/README.adoc[Observability Services] | Management and Monitoring | An example showing how to use Camel with Observability Services
|===
// examples: END

Expand Down
95 changes: 95 additions & 0 deletions observability-services/README.adoc
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
== Spring Boot Example with Camel Observability Services

=== Introduction

This example illustrates how to use https://projects.spring.io/spring-boot/[Spring Boot] with http://camel.apache.org[Camel] to demonstrate observability capabilities. It implements a REST service that generates random numbers with variable response times, showcasing distributed tracing, metrics collection, and monitoring through OpenTelemetry.

The project uses `camel-observability-services-starter` component for automatic instrumentation, `camel-platform-http-starter` for REST endpoints, and integrates with OpenTelemetry Java agent for comprehensive observability.

For additional information there is https://camel.apache.org/blog/2025/03/camel-observability[blog post]

=== Observability Stack

To run the complete observability stack with Jaeger and Prometheus:

[source,bash]
----
docker-compose up
----

This will start:

- OpenTelemetry Collector (ports 4317/4318) - collects traces and metrics
- Jaeger UI (http://localhost:16686) - distributed tracing visualization
- Prometheus (http://localhost:9090) - metrics collection and storage

The application, using agent, sends telemetry data to the OpenTelemetry Collector, which exports traces to Jaeger and metrics to Prometheus.

=== Run

You can run this example using:

[source,bash]
----
mvn spring-boot:run
----

After the Spring Boot application is started, you can execute the following HTTP requests:

[source,bash]
----
curl http://localhost:8080/api/random
----

The command will call the random number generator endpoint. Each call will:
- Generate a random number between 1-1000
- Simulate a random delay between 100-2000ms
- Return the number as response body
- Create traces and metrics for observability

You should see output similar to:

----
INFO 101511 --- [ task-1] generate-random-number : Generated random number: 742 with delay: 1250ms
----

=== Exposed Observability endpoints

The `camel-observability-services-starter` will configure the application and overrides the actuator setup so the health and metrics (in prometheus format) endpoints will be

```
http://localhost:9876/observe/health

http://localhost:9876/observe/metrics
```

even if in this example the metrics will be distributed using OpenTelemetry agent and not scraping the `/observe/metrics` endpoint

=== Testing Observability

1. **Generate some traffic:**
[source,bash]
----
for i in {1..10}; do curl http://localhost:8080/api/random; echo; sleep 1; done
----

2. **View traces in Jaeger:**
- Open http://localhost:16686
- Select service and search for traces

3. **View metrics in Prometheus:**
- Open http://localhost:9090
- Query metrics like `camel_route_exchange_completed_total`


The Spring Boot application can be stopped pressing `[CTRL] + [C]` in the shell.

=== Help and contributions

If you hit any problem using Camel or have some feedback, then please
https://camel.apache.org/community/support/[let us know].

We also love contributors, so
https://camel.apache.org/community/contributing/[get involved] :-)

The Camel riders!
38 changes: 38 additions & 0 deletions observability-services/docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
version: "3.9"

services:

otel-collector:
image: otel/opentelemetry-collector:latest
command:
- --config=/etc/otelcol-cont/otel-collector.yml
volumes:
- ./otel-collector.yml:/etc/otelcol-cont/otel-collector.yml
ports:
- "4318:4318" # OTLP http receiver
- "4317:4317" # OTLP grpc receiver
depends_on:
- jaeger-all-in-one
- prometheus

jaeger-all-in-one:
image: quay.io/jaegertracing/all-in-one:latest
restart: always
ports:
- "16686:16686"

prometheus:
image: prom/prometheus:latest
container_name: prometheus
restart: always
ports:
- "9090:9090"
volumes:
- ./prometheus.yml:/etc/prometheus/prometheus.yml
command:
- '--config.file=/etc/prometheus/prometheus.yml'
- '--storage.tsdb.path=/prometheus'
- '--web.console.libraries=/etc/prometheus/console_libraries'
- '--web.console.templates=/etc/prometheus/consoles'
- '--storage.tsdb.retention.time=200h'
- '--web.enable-lifecycle'
31 changes: 31 additions & 0 deletions observability-services/otel-collector.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
receivers:
otlp:
protocols:
grpc:
endpoint: 0.0.0.0:4317
http:
endpoint: 0.0.0.0:4318

processors:
batch:

exporters:
debug:
verbosity: detailed
otlp/jaeger:
endpoint: jaeger-all-in-one:4317
tls:
insecure: true
prometheus:
endpoint: "0.0.0.0:8889"

service:
pipelines:
traces:
receivers: [otlp]
processors: [batch]
exporters: [debug,otlp/jaeger]
metrics:
receivers: [otlp]
processors: [batch]
exporters: [debug,prometheus]
145 changes: 145 additions & 0 deletions observability-services/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,145 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--

Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

-->
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">

<modelVersion>4.0.0</modelVersion>

<parent>
<groupId>org.apache.camel.springboot.example</groupId>
<artifactId>examples</artifactId>
<version>4.15.0-SNAPSHOT</version>
</parent>

<artifactId>camel-example-spring-boot-observability-services</artifactId>
<name>Camel SB Examples :: Observability Services</name>
<description>This example shows how to work with Apache Camel observability services using Spring Boot</description>

<properties>
<category>Management and Monitoring</category>
<opentelemetry-agent.version>2.19.0</opentelemetry-agent.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
</properties>

<dependencyManagement>
<dependencies>
<!-- Camel BOM -->
<dependency>
<groupId>org.apache.camel.springboot</groupId>
<artifactId>camel-spring-boot-bom</artifactId>
<version>${project.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!-- Spring Boot BOM -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot-version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>

<dependencies>
<!-- spring-boot -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>

<!-- Camel -->
<dependency>
<groupId>org.apache.camel.springboot</groupId>
<artifactId>camel-spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.apache.camel.springboot</groupId>
<artifactId>camel-observability-services-starter</artifactId>
</dependency>
<dependency>
<groupId>org.apache.camel.springboot</groupId>
<artifactId>camel-platform-http-starter</artifactId>
</dependency>

</dependencies>

<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<executions>
<execution>
<id>copy-javaagent</id>
<phase>process-resources</phase>
<goals>
<goal>copy</goal>
</goals>
<configuration>
<artifactItems>
<artifactItem>
<groupId>io.opentelemetry.javaagent</groupId>
<artifactId>opentelemetry-javaagent</artifactId>
<version>${opentelemetry-agent.version}</version>
<overWrite>true</overWrite>
<outputDirectory>${project.build.directory}/javaagents</outputDirectory>
<destFileName>javaagent.jar</destFileName>
</artifactItem>
</artifactItems>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>${spring-boot-version}</version>
<configuration>
<agents>
<agent>${project.build.directory}/javaagents/javaagent.jar</agent>
</agents>
<environmentVariables>
<OTEL_LOGS_EXPORTER>none</OTEL_LOGS_EXPORTER>
<OTEL_SERVICE_NAME>camel-observability-services</OTEL_SERVICE_NAME>
<OTEL_JMX_TARGET_SYSTEM>camel</OTEL_JMX_TARGET_SYSTEM>
</environmentVariables>
</configuration>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>

</project>
8 changes: 8 additions & 0 deletions observability-services/prometheus.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
global:
scrape_interval: 15s
evaluation_interval: 15s

scrape_configs:
- job_name: 'otel-collector'
static_configs:
- targets: ['otel-collector:8889']
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.camel.example.observability;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

//CHECKSTYLE:OFF
@SpringBootApplication
public class CamelObservabilityApplication {

public static void main(String[] args) {
SpringApplication.run(CamelObservabilityApplication.class, args);
}
}
// CHECKSTYLE:ON
Loading