Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Baremetal / Add stork consul scenario #572

Merged
merged 3 commits into from
Mar 21, 2022
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
10 changes: 10 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -651,6 +651,16 @@ this.router.get("/secured")
* authZ::authorize: custom AuthZ(authorization) provider.
* secure.helloWorld(rc): actual http endpoint (Rest layer).

### Service-discovery/stork

Verifies Stork integration in order to provide service discovering and round-robin load balancing between services

`StorkServiceDiscoveryIT` scenario deploys four services:
* Pung: is a simple endpoint that returns "pung" as a string
* Pong: is a simple endpoint that returns "pong" as a string
* PongReplica: is a "Pong service" replica, that is deployed in another physical service
* Ping: is the main client microservice that will use `pung` and `pong` (Pong and PongReplica) services. The service
discovery will be done by Stork, and the request dispatching between "pong" services is going to be done by Stork load balancer.

### `monitoring/microprofile`

Expand Down
1 change: 1 addition & 0 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -349,6 +349,7 @@
<module>docker-build</module>
<module>javaee-like-getting-started</module>
<module>scaling</module>
<module>service-discovery/stork</module>
<module>lifecycle-application</module>
<module>external-applications</module>
<module>scheduling/quartz</module>
Expand Down
67 changes: 67 additions & 0 deletions service-discovery/stork/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
<?xml version="1.0" encoding="UTF-8"?>
<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>io.quarkus.ts.qe</groupId>
<artifactId>parent</artifactId>
<version>1.0.0-SNAPSHOT</version>
<relativePath>../..</relativePath>
</parent>
<artifactId>stork</artifactId>
<packaging>jar</packaging>
<name>Quarkus QE TS: Service-discovery: Stork</name>
<dependencies>
<dependency>
<groupId>io.smallrye.stork</groupId>
<artifactId>stork-service-discovery-consul</artifactId>
</dependency>
<dependency>
<groupId>io.smallrye.reactive</groupId>
<artifactId>smallrye-mutiny-vertx-consul-client</artifactId>
</dependency>
<dependency>
<groupId>io.smallrye.stork</groupId>
<artifactId>stork-service-discovery-kubernetes</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-reactive-routes</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-rest-client-reactive</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus.qe</groupId>
<artifactId>quarkus-test-service-consul</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<profiles>
<!-- Skipped on Windows as does not support Linux Containers / Testcontainers -->
<profile>
<id>skip-tests-on-windows</id>
<activation>
<os>
<family>windows</family>
</os>
</activation>
<build>
<plugins>
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<configuration>
<skip>true</skip>
</configuration>
</plugin>
<plugin>
<artifactId>maven-failsafe-plugin</artifactId>
<configuration>
<skip>true</skip>
</configuration>
</plugin>
</plugins>
</build>
</profile>
</profiles>
</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package io.quarkus.ts.stork;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;

import org.eclipse.microprofile.rest.client.inject.RegisterRestClient;
import org.jboss.resteasy.reactive.RestResponse;

import io.smallrye.mutiny.Uni;

@Path("/pong")
@RegisterRestClient(baseUri = "stork://pong")
public interface MyBackendPongProxy {
@GET
@Produces(MediaType.TEXT_PLAIN)
@Path("/")
Uni<RestResponse<String>> get();
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package io.quarkus.ts.stork;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;

import org.eclipse.microprofile.rest.client.inject.RegisterRestClient;

import io.smallrye.mutiny.Uni;

@Path("/pung")
@RegisterRestClient(baseUri = "stork://pung")
public interface MyBackendPungProxy {
@GET
@Produces(MediaType.TEXT_PLAIN)
@Path("/")
Uni<String> get();
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package io.quarkus.ts.stork;

import javax.ws.rs.WebApplicationException;
import javax.ws.rs.core.MediaType;

import org.eclipse.microprofile.rest.client.inject.RestClient;

import io.quarkus.vertx.web.Route;
import io.quarkus.vertx.web.RouteBase;
import io.smallrye.mutiny.Uni;
import io.vertx.ext.web.RoutingContext;

@RouteBase(path = "/ping", produces = MediaType.TEXT_PLAIN)
public class PingResource {

public static final String PING_PREFIX = "ping-";
public static final String HEADER_ID = "x-id";

@RestClient
MyBackendPongProxy pongService;

@RestClient
MyBackendPungProxy pungService;

@Route(methods = Route.HttpMethod.GET, path = "/pung")
public Uni<String> pung() {
return pungService.get()
.onFailure().transform(error -> new WebApplicationException(error.getMessage()))
.map(resp -> PING_PREFIX + resp);
}

@Route(methods = Route.HttpMethod.GET, path = "/pong")
public void pong(RoutingContext context) {
pongService.get().onFailure().transform(error -> new WebApplicationException(error.getMessage())).subscribe()
.with(resp -> context.response()
.putHeader(HEADER_ID, resp.getHeaderString(HEADER_ID))
.end(PING_PREFIX + resp.getEntity()));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
package io.quarkus.ts.stork;

import static io.quarkus.ts.stork.PongResource.PONG_SERVICE_NAME;

import javax.enterprise.event.Observes;
import javax.ws.rs.core.MediaType;

import org.eclipse.microprofile.config.inject.ConfigProperty;

import io.quarkus.runtime.StartupEvent;
import io.quarkus.vertx.web.Route;
import io.quarkus.vertx.web.RouteBase;
import io.smallrye.mutiny.Uni;
import io.vertx.ext.consul.ConsulClientOptions;
import io.vertx.ext.consul.ServiceOptions;
import io.vertx.mutiny.core.Vertx;
import io.vertx.mutiny.ext.consul.ConsulClient;

@RouteBase(path = "/pong", produces = MediaType.TEXT_PLAIN)
public class PongReplicaResource {

private static final String DEFAULT_PONG_REPLICA_RESPONSE = "pongReplica";

@ConfigProperty(name = "stork.pong-replica.service-discovery.consul-host", defaultValue = "localhost")
String host;
@ConfigProperty(name = "stork.pong-replica.service-discovery.consul-port", defaultValue = "8500")
String port;
@ConfigProperty(name = "pong-replica-service-port", defaultValue = "8080")
String pongPort;
@ConfigProperty(name = "pong-replica-service-host", defaultValue = "localhost")
String pongHost;
@ConfigProperty(name = "stork.pong-replica.service-discovery", defaultValue = "consul")
String serviceDiscoveryType;

public void init(@Observes StartupEvent ev, Vertx vertx) {
if (serviceDiscoveryType.equalsIgnoreCase("consul")) {
ConsulClient client = ConsulClient.create(vertx,
new ConsulClientOptions().setHost(host).setPort(Integer.parseInt(port)));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this.port, if you don't mind. Also, can't we have integer ConfigProperties?


client.registerServiceAndAwait(
new ServiceOptions().setPort(Integer.parseInt(pongPort)).setAddress(pongHost).setName(PONG_SERVICE_NAME)
.setId("pongReplica"));
}
}

@Route(path = "/", methods = Route.HttpMethod.GET)
public Uni<String> pong() {
return Uni.createFrom().item(DEFAULT_PONG_REPLICA_RESPONSE);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
package io.quarkus.ts.stork;

import java.util.UUID;

import javax.enterprise.event.Observes;
import javax.ws.rs.core.MediaType;

import org.eclipse.microprofile.config.inject.ConfigProperty;

import io.quarkus.runtime.StartupEvent;
import io.quarkus.vertx.web.Route;
import io.quarkus.vertx.web.RouteBase;
import io.vertx.ext.consul.ConsulClientOptions;
import io.vertx.ext.consul.ServiceOptions;
import io.vertx.ext.web.RoutingContext;
import io.vertx.mutiny.core.Vertx;
import io.vertx.mutiny.ext.consul.ConsulClient;

@RouteBase(path = "/pong", produces = MediaType.TEXT_PLAIN)
public class PongResource {

public static final String PONG_SERVICE_NAME = "pong";
private static final String DEFAULT_PONG_RESPONSE = "pong";
private static final String HEADER_ID = "x-id";
private String instanceUniqueId;

@ConfigProperty(name = "stork.pong.service-discovery.consul-host", defaultValue = "localhost")
String host;
@ConfigProperty(name = "stork.pong.service-discovery.consul-port", defaultValue = "8500")
String port;
@ConfigProperty(name = "pong-service-port", defaultValue = "8080")
String pongPort;
@ConfigProperty(name = "pong-service-host", defaultValue = "localhost")
String pongHost;
@ConfigProperty(name = "stork.pong.service-discovery", defaultValue = "consul")
String serviceDiscoveryType;

public void init(@Observes StartupEvent ev, Vertx vertx) {
instanceUniqueId = UUID.randomUUID().toString();
if (serviceDiscoveryType.equalsIgnoreCase("consul")) {
ConsulClient client = ConsulClient.create(vertx,
new ConsulClientOptions().setHost(host).setPort(Integer.parseInt(port)));

client.registerServiceAndAwait(
new ServiceOptions().setPort(Integer.parseInt(pongPort)).setAddress(pongHost).setName(PONG_SERVICE_NAME)
.setId("pong"));
}
}

@Route(path = "/", methods = Route.HttpMethod.GET)
public void pong(final RoutingContext context) {
context.response().putHeader(HEADER_ID, instanceUniqueId).end(DEFAULT_PONG_RESPONSE);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
package io.quarkus.ts.stork;

import javax.enterprise.event.Observes;
import javax.ws.rs.core.MediaType;

import org.eclipse.microprofile.config.inject.ConfigProperty;

import io.quarkus.runtime.StartupEvent;
import io.quarkus.vertx.web.Route;
import io.quarkus.vertx.web.RouteBase;
import io.smallrye.mutiny.Uni;
import io.vertx.ext.consul.ConsulClientOptions;
import io.vertx.ext.consul.ServiceOptions;
import io.vertx.mutiny.core.Vertx;
import io.vertx.mutiny.ext.consul.ConsulClient;

@RouteBase(path = "/pung", produces = MediaType.TEXT_PLAIN)
public class PungResource {

@ConfigProperty(name = "stork.pung.service-discovery.consul-host", defaultValue = "localhost")
String host;
@ConfigProperty(name = "stork.pung.service-discovery.consul-port", defaultValue = "8500")
String port;
@ConfigProperty(name = "pung-service-port", defaultValue = "8080")
String pungPort;
@ConfigProperty(name = "pung-service-host", defaultValue = "localhost")
String pungHost;
@ConfigProperty(name = "stork.pung.service-discovery", defaultValue = "consul")
String serviceDiscoveryType;

public void init(@Observes StartupEvent ev, Vertx vertx) {
if (serviceDiscoveryType.equalsIgnoreCase("consul")) {
ConsulClient client = ConsulClient.create(vertx,
new ConsulClientOptions().setHost(host).setPort(Integer.parseInt(port)));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here, and everywhere in Resources:

Suggested change
new ConsulClientOptions().setHost(host).setPort(Integer.parseInt(port)));
new ConsulClientOptions().setHost(host).setPort(Integer.parseInt(this.port)));

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's keep it as it's other modules. there is no a team agreement about that

Copy link
Contributor Author

@pjgg pjgg Mar 21, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Currently, we are following this principle: https://checkstyle.sourceforge.io/config_coding.html#RequireThis
But is true that is not added to checkstyle template

<module name="RequireThis">
  <property name="validateOnlyOverlapping" value="true"/>
</module>


client.registerServiceAndAwait(
new ServiceOptions().setPort(Integer.parseInt(pungPort)).setAddress(pungHost).setName("pung")
.setId("pung"));
}
}

@Route(path = "/", methods = Route.HttpMethod.GET)
public Uni<String> pung() {
return Uni.createFrom().item("pung");
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# application properties should be here
# TODO https://github.com/quarkusio/quarkus/issues/24444
quarkus.native.additional-build-args=--allow-incomplete-classpath, --initialize-at-run-time=io.fabric8.kubernetes.client.internal.CertUtils, --enable-url-protocols=https
Loading