Skip to content

Commit

Permalink
include otel
Browse files Browse the repository at this point in the history
  • Loading branch information
tsanderConsol committed Jun 18, 2024
1 parent c15bc5e commit e2d7000
Show file tree
Hide file tree
Showing 13 changed files with 279 additions and 7 deletions.
2 changes: 2 additions & 0 deletions agent.properties
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
otel.exporter.otlp.protocol=http/protobuf
otel.exporter.otlp.timeout=60000
25 changes: 25 additions & 0 deletions datasource.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# config file version
apiVersion: 1

datasources:
- name: Clickhouse
type: grafana-clickhouse-datasource
jsonData:
defaultDatabase: otel
port: 8123
server: host.docker.internal
protocol: http
username: test
tlsSkipVerify: true
logs:
defaultDatabase: otel
defaultTable: otel_logs
otelEnabled: true
otelVersion: 1.2.9
traces:
defaultDatabase: otel
defaultTable: otel_traces
otelEnabled: true
otelVersion: 1.2.9
secureJsonData:
password: test
13 changes: 13 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
version: '3.8'

services:
grafana:
image: grafana/grafana:latest
ports:
- "3001:3000"
volumes:
- ./grafana.ini:/etc/grafana/grafana.ini
#- ./datasource.yaml:/etc/grafana/provisioning/datasources/datasource.yaml
environment:
GF_INSTALL_PLUGINS: grafana-clickhouse-datasource,vertamedia-clickhouse-datasource
GF_PLUGINS_ALLOW_LOADING_UNSIGNED_PLUGINS: vertamedia-clickhouse-datasource
10 changes: 10 additions & 0 deletions grafana.ini
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
[auth]
disable_login_form = true

[auth.anonymous]
enabled = true
org_name = Main Org.
org_role = Admin

[users]
default_theme = light
Binary file added opentelemetry-javaagent.jar
Binary file not shown.
49 changes: 47 additions & 2 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -15,14 +15,27 @@
<description>TestContainersDemoSB</description>
<properties>
<java.version>17</java.version>
<aws-sdk.version>2.25.19</aws-sdk.version>
<testcontainers.version>1.19.7</testcontainers.version>
<aws-sdk.version>2.26.3</aws-sdk.version>
<otel.version>1.39.0</otel.version>
<testcontainers.version>1.19.8</testcontainers.version>
<clickhouse-driver.version>0.6.1</clickhouse-driver.version>
<apache-http.version>5.3</apache-http.version>
<lz4.version>1.8.0</lz4.version>
</properties>

<dependencies>
<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>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>software.amazon.awssdk</groupId>
<artifactId>dynamodb</artifactId>
Expand Down Expand Up @@ -55,6 +68,31 @@
<version>${testcontainers.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.testcontainers</groupId>
<artifactId>clickhouse</artifactId>
<version>${testcontainers.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.clickhouse</groupId>
<artifactId>clickhouse-jdbc</artifactId>
<version>${clickhouse-driver.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.httpcomponents.client5</groupId>
<artifactId>httpclient5</artifactId>
<version>${apache-http.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.lz4</groupId>
<artifactId>lz4-java</artifactId>
<version>${lz4.version}</version>
<scope>test</scope>
</dependency>

</dependencies>

<build>
Expand All @@ -65,5 +103,12 @@
</plugin>
</plugins>
</build>
<repositories>
<repository>
<id>maven_central</id>
<name>Maven Central</name>
<url>https://repo.maven.apache.org/maven2/</url>
</repository>
</repositories>

</project>
5 changes: 5 additions & 0 deletions run.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
export JAVA_TOOL_OPTIONS="-javaagent:opentelemetry-javaagent.jar"
export OTEL_SERVICE_NAME="Testcontainers"
export OTEL_JAVAAGENT_CONFIGURATION_FILE="agent.properties"
#export OTEL_METRICS_EXPORTER="otlp"
mvn clean install
Original file line number Diff line number Diff line change
@@ -1,12 +1,18 @@
package com.consol;

import io.micrometer.core.instrument.MeterRegistry;
import io.micrometer.core.instrument.Metrics;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.context.annotation.Bean;

import java.util.Optional;

@SpringBootApplication
public class TestContainersDemoSbApplication {

public static void main(String[] args) {
public static void main(final String[] args) {
SpringApplication.run(TestContainersDemoSbApplication.class, args);
}

Expand Down
13 changes: 13 additions & 0 deletions src/main/java/com/consol/boundary/PersonResource.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

import java.util.Optional;

import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE;

@RestController
Expand All @@ -32,4 +34,15 @@ public ResponseEntity<PersonTO> getPerson(@PathVariable("uuid") final String uui
LOGGER.info("Received GET with uuid: {}", uuid);
return ResponseEntity.ok(personService.getPersonById(uuid));
}

@GetMapping(value = "/person/random", produces = APPLICATION_JSON_VALUE)
public ResponseEntity<PersonTO> getRandomPerson() {
return ResponseEntity.ok(personService.getRandomPerson());
}

@GetMapping(value = "/person/failRandom", produces = APPLICATION_JSON_VALUE)
public ResponseEntity<PersonTO> fail() {
final Optional<PersonTO> personTO = personService.fail();
return personTO.map(ResponseEntity::ok).orElseGet(() -> ResponseEntity.internalServerError().build());
}
}
30 changes: 27 additions & 3 deletions src/main/java/com/consol/control/PersonService.java
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,9 @@
import software.amazon.awssdk.services.dynamodb.model.GetItemRequest;
import software.amazon.awssdk.services.dynamodb.model.PutItemRequest;

import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.UUID;

@Service
Expand All @@ -21,15 +23,21 @@ public class PersonService {

private final DynamoDbClient dynamoDbClient;
private final String tableName;
private final Randomizer randomizer;

public PersonService(final DynamoDbClient dynamoDbClient, @Value("${dynamodb.tablename}") final String tableName) {
public PersonService(
final DynamoDbClient dynamoDbClient,
@Value("${dynamodb.tablename}") final String tableName,
final Randomizer randomizer
) {
this.dynamoDbClient = dynamoDbClient;
this.tableName = tableName;
this.randomizer = randomizer;
}

public IdTO store(final PersonTO personTO) {
final String uuid = UUID.randomUUID().toString();
LOGGER.debug("Storing person with ID: {}", uuid);
LOGGER.info("Storing person with ID: {}", uuid);
dynamoDbClient.putItem(
PutItemRequest.builder()
.tableName(tableName)
Expand All @@ -47,7 +55,7 @@ public IdTO store(final PersonTO personTO) {
}

public PersonTO getPersonById(final String uuid) {
LOGGER.debug("Fetching person for ID: {}", uuid);
LOGGER.info("Fetching person for ID: {}", uuid);
final Map<String, AttributeValue> values = dynamoDbClient.getItem(
GetItemRequest.builder()
.tableName(tableName)
Expand All @@ -60,4 +68,20 @@ public PersonTO getPersonById(final String uuid) {
Integer.parseInt(values.get("age").n())
);
}

public PersonTO getRandomPerson() {
LOGGER.info("Fetching a random persons");
return new PersonTO(randomizer.getRandomFirstName(), randomizer.getRandomLastName(), randomizer.getRandomAge());
}

public Optional<PersonTO> fail() {
LOGGER.info("Fail Fetching a random person");
if(randomizer.getRandomAge() %2 == 0) {
LOGGER.info("Got a person");
return Optional.of(getRandomPerson());
} else {
LOGGER.error("Did not get a person.");
return Optional.empty();
}
}
}
25 changes: 25 additions & 0 deletions src/main/java/com/consol/control/Randomizer.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
package com.consol.control;

import org.springframework.stereotype.Component;

import java.util.Random;

@Component
public class Randomizer {

private final Random random = new Random();
private final String[] firstNames = {"Hans", "Peter", "Gabi"};
private final String[] lastNames = {"Meier", "Schmitt", "Bauer"};

public String getRandomFirstName() {
return firstNames[random.nextInt(firstNames.length)];
}

public String getRandomLastName() {
return lastNames[random.nextInt(lastNames.length)];
}

public int getRandomAge() {
return random.nextInt(100);
}
}
66 changes: 65 additions & 1 deletion src/test/java/com/consol/CrudTest.java
Original file line number Diff line number Diff line change
@@ -1,39 +1,86 @@
package com.consol;

import com.consol.entity.PersonTO;
import com.github.dockerjava.api.model.ExposedPort;
import com.github.dockerjava.api.model.PortBinding;
import com.github.dockerjava.api.model.Ports;
import io.restassured.http.ContentType;
import org.junit.jupiter.api.AfterAll;
import org.junit.jupiter.api.BeforeAll;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
import org.testcontainers.clickhouse.ClickHouseContainer;
import org.testcontainers.containers.GenericContainer;
import org.testcontainers.containers.Network;
import org.testcontainers.containers.localstack.LocalStackContainer;
import org.testcontainers.junit.jupiter.Testcontainers;
import org.testcontainers.utility.DockerImageName;
import org.testcontainers.utility.MountableFile;

import java.sql.ResultSet;
import java.util.List;

import static io.restassured.RestAssured.given;

@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT)
@Testcontainers
class CrudTest {

static Network network = Network.newNetwork();

static LocalStackContainer localStack =
new LocalStackContainer(DockerImageName.parse("localstack/localstack"))
.withCopyFileToContainer(
MountableFile.forHostPath("src/test/resources/init-resources.sh"),
"/etc/localstack/init/ready.d/init-resources.sh"
)
.withNetwork(network);

static ClickHouseContainer clickHouseContainer =
new ClickHouseContainer(DockerImageName.parse("clickhouse/clickhouse-server"))
.withNetwork(network)
.withDatabaseName("otel")
.withUsername("test")
.withPassword("test")
.withExposedPorts(8123)
.withNetworkAliases("clickhouse")
.withCreateContainerCmdModifier(cmd -> cmd
.withPortBindings(new PortBinding(Ports.Binding.bindPort(8123), new ExposedPort(8123)))
);

static GenericContainer<?> otelCollector =
new GenericContainer<>(DockerImageName.parse("otel/opentelemetry-collector-contrib:latest-arm64"))
.withCopyToContainer(
MountableFile.forHostPath("src/test/resources/config.yaml"),
"/etc/otelcol-contrib/config.yaml"
)
.withNetwork(network)
.dependsOn(clickHouseContainer)
.withExposedPorts(4317)
.withExposedPorts(4318)
.withCreateContainerCmdModifier(cmd -> cmd.getHostConfig()
.withPortBindings(List.of(
new PortBinding(Ports.Binding.bindPort(4317), new ExposedPort(4317)),
new PortBinding(Ports.Binding.bindPort(4318), new ExposedPort(4318))
))
);

@BeforeAll
static void init() {
localStack.start();
clickHouseContainer.start();
otelCollector.start();
}

@AfterAll
static void stop() {
localStack.stop();
clickHouseContainer.stop();
otelCollector.stop();
}

@DynamicPropertySource
Expand All @@ -42,10 +89,21 @@ static void configureProperties(final DynamicPropertyRegistry dynamicPropertyReg
dynamicPropertyRegistry.add("aws.secretKeyId", () -> localStack.getSecretKey());
dynamicPropertyRegistry.add("dynamodb.endpoint", () -> localStack.getEndpoint());
dynamicPropertyRegistry.add("dynamodb.tablename", () -> "test");
dynamicPropertyRegistry.add("spring.datasource.url", () -> "jdbc:ch://localhost:8123/otel");
dynamicPropertyRegistry.add("spring.datasource.username", () -> "test");
dynamicPropertyRegistry.add("spring.datasource.password", () -> "test");
dynamicPropertyRegistry.add("spring.datasource.driver-class-name", () -> "com.clickhouse.jdbc.ClickHouseDriver");
}

@Autowired
JdbcTemplate jdbcTemplate;

@Test
void postAndGet() {
void postAndGet() throws InterruptedException {

List<Long> result = jdbcTemplate.query("select count(*) from otel_metrics_histogram", (rs, rowNum) -> rs.getLong(1));
assert result.size() == 1;
assert result.get(0) == 0;

final PersonTO personIn = new PersonTO("John", "Doe", 30);

Expand All @@ -68,5 +126,11 @@ void postAndGet() {
.as(PersonTO.class);

assert personIn.equals(personOut);

Thread.sleep(5000);

result = jdbcTemplate.query("select count(*) from otel_metrics_histogram", (rs, rowNum) -> rs.getLong(1));
assert result.size() == 1;
assert result.get(0) > 0;
}
}
Loading

0 comments on commit e2d7000

Please sign in to comment.