Cześć wszystkim! Oto on – nasz ostatni post z serii o Quarkus! (A propos, zobaczcie nasz webinar . Pokażemy, jak zacząć „od zera” lub przenieść gotowe rozwiązania)

W w poście omówiliśmy odpowiednie narzędzia, za pomocą których można ilościowo ocenić udoskonalenia wynikające z modernizacji aplikacji Java.
Od wersji 0.17.0, obsługuje użycie Advanced Message Queuing Protocol (), który jest otwartym standardem wymiany wiadomości biznesowych między aplikacjami lub organizacjami.
– to usługa zbudowana na podstawie otwartego projektu i implementująca mechanizm wymiany wiadomości oparty na platformie . Dowiedz się więcej o tym, jak to działa, przeczytaj . Dziś pokażemy, jak połączyć AMQ Online z Quarkus, aby zbudować nowoczesny system wymiany wiadomości na OpenShift, wykorzystując dwie nowe technologie związane z przetwarzaniem wiadomości.
Zakłada się, że już wdrożyłeś AMQ Online na platformie OpenShift (jeśli nie, zobacz ).
Na początek stworzymy aplikację Quarkus, która będzie przedstawiać prosty system przetwarzania zamówień z użyciem reaktywnej wymiany wiadomości. Ta aplikacja będzie zawierać generator zamówień, który wysyła zamówienia do kolejki wiadomości z ustalonym interwałem, oraz przetwornik zamówień, który będzie obsługiwał wiadomości z kolejki i tworzył potwierdzenia dostępne do przeglądania w przeglądarce.
Po utworzeniu aplikacji pokażemy, jak wprowadzić w nią konfigurację systemu wymiany wiadomości i wykorzystamy AMQ Online, aby zainicjować potrzebne nam zasoby na tym systemie.
Aplikacja Quarkus
Nasza aplikacja Quarkus działa na OpenShift i jest zmodyfikowaną wersją programu . Pełny przykład części klienckiej można znaleźć .
Generator zamówień
Generator co 5 sekund monotonnie przesyła rosnące identyfikatory zamówień na adres „orders”.
@ApplicationScoped
public class OrderGenerator {
private int orderId = 1;
@Outgoing("orders")
public Flowable generate() {
return Flowable.interval(5, TimeUnit.SECONDS)
.map(tick -> orderId++);
}
}
Przetwornik zamówień
Przetwornik zamówień jest jeszcze prostszy, po prostu zwraca identyfikator potwierdzenia na adres „confirmations”.
@ApplicationScoped
public class OrderProcessor {
@Incoming("orders")
@Outgoing("confirmations")
public Integer process(Integer order) {
// Identyfikator potwierdzenia jest równy podwojonemu identyfikatorowi zamówienia <img draggable="false" class="emoji" alt=":-)" src="https://s.w.org/images/core/emoji/11.2.0/svg/1f642.svg">
return order * 2;
}
}
Zasoby potwierdzeń
Zasób potwierdzenia to punkt końcowy HTTP do listowania potwierdzeń utworzonych przez nasze aplikacje.
@Path("/confirmations")
public class ConfirmationResource {
@Inject
@Stream("confirmations") Publisher orders;
@GET
@Produces(MediaType.TEXT_PLAIN)
public String hello() {
return "hello";
}
@GET
@Path("/stream")
@Produces(MediaType.SERVER_SENT_EVENTS)
public Publisher stream() {
return orders;
}
}
Konfiguracja
Aby połączyć się z AMQ Online, nasza aplikacja potrzebuje pewnych danych konfiguracyjnych, a mianowicie: konfiguracji konektora Quarkus, informacji o punkcie końcowym AMQP oraz danych uwierzytelniających klienta. Oczywiście, najlepiej trzymać wszystkie dane konfiguracyjne w jednym miejscu, jednak specjalnie je rozdzielimy, aby pokazać możliwe opcje konfiguracji aplikacji Quarkus.
Konektory
Konfigurację konektora można podać na etapie kompilacji za pomocą pliku właściwości aplikacji:
mp.messaging.outgoing.orders.connector=smallrye-amqp
mp.messaging.incoming.orders.connector=smallrye-amqp
Aby nie komplikować, będziemy używać kolejki wiadomości tylko dla adresu „orders”. Natomiast adres „confirmations” w naszej aplikacji będzie korzystał z kolejki w pamięci.
Punkt końcowy AMQP
Na etapie kompilacji nazwa hosta i numer portu dla punktu końcowego AMQP są nieznane, dlatego należy je wstrzyknąć. Punkt końcowy można określić w configmap, który jest tworzony przez AMQ Online, dlatego zdefiniujemy je za pomocą zmiennych środowiskowych w manifeście aplikacji:
spec:
template:
spec:
containers:
- env:
- name: AMQP_HOST
valueFrom:
configMapKeyRef:
name: quarkus-config
key: service.host
- name: AMQP_PORT
valueFrom:
configMapKeyRef:
name: quarkus-config
key: service.port.amqp
Dane uwierzytelniające
Token konta usługi można wykorzystać do uwierzytelnienia naszej aplikacji w OpenShift. W tym celu najpierw należy utworzyć niestandardowy ConfigSource, który będzie odczytywał token uwierzytelniający z systemu plików pod’a:
public class MessagingCredentialsConfigSource implements ConfigSource {
private static final Set propertyNames;
static {
propertyNames = new HashSet();
propertyNames.add("amqp-username");
propertyNames.add("amqp-password");
}
@Override
public Set getPropertyNames() {
return propertyNames;
}
@Override
public Map getProperties() {
try {
Map properties = new HashMap();
properties.put("amqp-username", "@@serviceaccount@@");
properties.put("amqp-password", readTokenFromFile());
return properties;
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
@Override
public String getValue(String key) {
if ("amqp-username".equals(key)) {
return "@@serviceaccount@@";
}
if ("amqp-password".equals(key)) {
try {
return readTokenFromFile();
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
return null;
}
@Override
public String getName() {
return "messaging-credentials-config";
}
private static String readTokenFromFile() throws IOException {
return new String(Files.readAllBytes(Paths.get("/var/run/secrets/kubernetes.io/serviceaccount/token")), StandardCharsets.UTF_8);
}
}
Budowanie i wdrażanie aplikacji
Ponieważ aplikację trzeba skompilować do pliku wykonywalnego, potrzebna będzie maszyna wirtualna GraalVM. Szczegóły dotyczące konfiguracji środowiska można znaleźć w odpowiednich instrukcjach w .
Następnie, postępując zgodnie z tamtejszymi instrukcjami, należy pobrać źródła, przeprowadzić budowę i wykonać wdrożenie naszej aplikacji:
git clone https://github.com/EnMasseProject/enmasse-example-clients
cd enmasse-example-clients/quarkus-example-client
oc new-project myapp
mvn -Pnative -Dfabric8.mode=openshift -Dfabric8.build.strategy=docker package fabric8:build fabric8:resource fabric8:apply
Po tych poleceniach aplikacja będzie wdrożona, ale nie uruchomi się, dopóki nie skonfigurujemy w AMQ Online potrzebnych zasobów komunikacji.
Konfiguracja systemu komunikacji
Teraz należy określić w systemie komunikacji zasoby, które są potrzebne naszej aplikacji. W tym celu trzeba stworzyć: 1) przestrzeń adresową, aby zainicjować punkt końcowy systemu komunikacji; 2) adres, aby skonfigurować adresy, które wykorzystujemy w aplikacji; 3) użytkownika systemu komunikacji, aby ustawić dane uwierzytelniające klienta.
Przestrzeń adresowa
Obiekt AddressSpace w AMQ Online to zbiór adresów, które wspólnie korzystają z punktów końcowych połączenia oraz polityk uwierzytelniania i autoryzacji. Podczas tworzenia przestrzeni adresowej można określić, jak będą udostępniane punkty końcowe systemu komunikacji:
apiVersion: enmasse.io/v1beta1
kind: AddressSpace
metadata:
name: quarkus-example
spec:
type: brokered
plan: brokered-single-broker
endpoints:
- name: messaging
service: messaging
exports:
- name: quarkus-config
kind: configmap
Adresy
Adresy są używane do wysyłania i odbierania wiadomości. Każdy adres ma typ, który określa jego semantykę, a także plan, który określa liczbę zarezerwowanych zasobów. Adres można zdefiniować na przykład w ten sposób:
apiVersion: enmasse.io/v1beta1
kind: Address
metadata:
name: quarkus-example.orders
spec:
address: orders
type: queue
plan: brokered-queue
Użytkownik systemu wymiany wiadomości
Aby tylko zaufane aplikacje mogły wysyłać i odbierać wiadomości na twoich adresach, w systemie wymiany wiadomości należy utworzyć użytkownika. Dla aplikacji działających w klastrze klienci mogą być uwierzytelniani za pomocą konta usługi OpenShift. Użytkownika "serviceaccount" można zdefiniować na przykład tak:
apiVersion: user.enmasse.io/v1beta1
kind: MessagingUser
metadata:
name: quarkus-example.app
spec:
username: system:serviceaccount:myapp:default
authentication:
type: serviceaccount
authorization:
- operations: ["send", "recv"]
addresses: ["orders"]
Uprawnienia do konfiguracji aplikacji
Aby AMQ Online mógł utworzyć configmap, którego użyliśmy do wdrożenia informacji o końcowym punkcie AMQP, należy zdefiniować rolę i powiązanie roli (Role i RoleBinding):
---
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: quarkus-config
spec:
rules:
- apiGroups: [ "" ]
resources: [ "configmaps" ]
verbs: [ "create" ]
- apiGroups: [ "" ]
resources: [ "configmaps" ]
resourceNames: [ "quarkus-config" ]
verbs: [ "get", "update", "patch" ]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
name: quarkus-config
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: quarkus-config
subjects:
- kind: ServiceAccount
name: address-space-controller
namespace: amq-online-infra
Jak zastosować konfiguracje
Konfigurację systemu wymiany wiadomości można zastosować w ten sposób:
cd enmasse-example-clients/quarkus-example-client
oc project myapp
oc apply -f src/main/resources/k8s/addressspace
oc apply -f src/main/resources/k8s/address
Weryfikacja aplikacji
Aby upewnić się, że aplikacja została uruchomiona, najpierw sprawdźmy, czy odpowiednie adresy zostały utworzone i są aktywne:
until [[ `oc get address quarkus-example.prices -o jsonpath='{.status.phase}'` == "Active" ]]; do echo "Jeszcze nie gotowe"; sleep 5; done
Następnie sprawdźmy URL trasy aplikacji (po prostu otworzymy ten adres w przeglądarce):
echo "http://$(oc get route quarkus-example-client -o jsonpath='{.spec.host}')/prices.html"
W przeglądarce powinno być widać, że bilety okresowo się aktualizują, gdy wiadomości są wysyłane i odbierane przez AMQ Online.
Podsumowując
Stworzyliśmy aplikację Quarkus, która wykorzystuje AMQP do wymiany wiadomości, skonfigurowaliśmy tę aplikację do działania na platformie Red Hat OpenShift, a także wdrożyliśmy jej konfigurację opartą na AMQ Online. Następnie stworzyliśmy manifesty niezbędne do zainicjowania systemu wymiany wiadomości dla naszej aplikacji.
Na tym kończymy serię o Quarkus, ale przed nami wiele nowości i interesujących rzeczy, zostawajcie z nami!
Źródło: habr.com
