JavaRush /Blog Java /Random-PL /Przewodnik po mikrousługach Java. Część 3: pytania ogólne...

Przewodnik po mikrousługach Java. Część 3: pytania ogólne

Opublikowano w grupie Random-PL
Tłumaczenie i adaptacja mikrousług Java: praktyczny przewodnik . Poprzednie części poradnika: Przyjrzyjmy się nieodłącznym problemom mikrousług w Javie, zaczynając od rzeczy abstrakcyjnych, a kończąc na konkretnych bibliotekach. Przewodnik po mikrousługach Java.  Część 3: pytania ogólne - 1

Jak zapewnić odporność mikrousługi Java?

Przypomnij sobie, że tworząc mikrousługi, zasadniczo zamieniasz wywołania metod JVM na synchroniczne wywołania HTTP lub asynchroniczne przesyłanie wiadomości. Chociaż w większości przypadków gwarantowane jest zakończenie wywołania metody (z wyjątkiem nieoczekiwanego zamknięcia maszyny JVM), wywołanie sieciowe jest domyślnie zawodne. Może działać, ale może nie działać z różnych powodów: sieć jest przeciążona, wdrożono nową regułę zapory sieciowej i tak dalej. Aby zobaczyć, jakie to ma znaczenie, spójrzmy na przykład BillingService.

Wzorce odporności HTTP/REST

Załóżmy, że klienci mogą kupować e-booki w witrynie Twojej firmy. Aby to zrobić, właśnie zaimplementowałeś mikrousługę rozliczeniową, która może wywołać Twój sklep internetowy w celu wygenerowania rzeczywistych faktur w formacie PDF. Na razie będziemy wykonywać to wywołanie synchronicznie, za pośrednictwem protokołu HTTP (chociaż rozsądniej jest wywoływać tę usługę asynchronicznie, ponieważ generowanie pliku PDF nie musi być natychmiastowe z punktu widzenia użytkownika. Tego samego przykładu użyjemy w następnym sekcję i spójrz na różnice).
@Service
class BillingService {

    @Autowired
    private HttpClient client;

     public void bill(User user, Plan plan) {
        Invoice invoice = createInvoice(user, plan);
        httpClient.send(invoiceRequest(user.getEmail(), invoice), responseHandler());
        // ...
    }
}
Podsumowując, oto trzy możliwe wyniki tego wywołania HTTP.
  • OK: połączenie zostało zrealizowane, konto zostało pomyślnie utworzone.
  • OPÓŹNIENIE: Połączenie zostało zrealizowane, ale jego ukończenie trwało zbyt długo.
  • BŁĄD. Połączenie nie powiodło się, być może wysłałeś niezgodne żądanie lub system może nie działać.
Od każdego programu oczekuje się obsługi sytuacji błędów, a nie tylko tych pomyślnych. To samo tyczy się mikroserwisów. Nawet jeśli musisz włożyć dodatkowy wysiłek, aby upewnić się, że wszystkie wdrożone wersje API są kompatybilne, gdy zaczniesz od wdrożeń i wydań poszczególnych mikrousług. Przewodnik po mikrousługach Java.  Część 3: pytania ogólne - 2Ciekawym przypadkiem, któremu warto się przyjrzeć, jest przypadek opóźnienia. Na przykład dysk twardy mikrousługi osoby odpowiadającej jest pełny i zamiast 50 ms, odpowiedź zajmuje 10 sekund. Sytuacja staje się jeszcze bardziej interesująca, gdy doświadczysz pewnego obciążenia, w wyniku którego brak reakcji Twojej usługi BillingService zacznie kaskadowo przechodzić przez Twój system. Jako ilustrujący przykład wyobraźmy sobie kuchnię powoli uruchamiającą „blok” wszystkich kelnerów w restauracji. Ta sekcja oczywiście nie może zapewnić wyczerpującego przeglądu tematu odporności mikrousług, ale służy jako przypomnienie programistom, że w rzeczywistości jest to coś, czym należy się zająć i nie można go ignorować przed wydaniem pierwszego wydania (co, z doświadczenia wynika, zdarza się częściej niż nie). następuje). Popularną biblioteką, która pomaga myśleć o opóźnieniach i odporności na awarie, jest Hystrix firmy Netflix. Skorzystaj z dokumentacji, aby zgłębić temat.

Wzorce odporności na wiadomości

Przyjrzyjmy się bliżej komunikacji asynchronicznej. Nasz program BillingService może teraz wyglądać mniej więcej tak, zakładając, że do przesyłania wiadomości używamy Spring i RabbitMQ. Aby utworzyć konto, wysyłamy teraz wiadomość do naszego brokera wiadomości RabbitMQ, gdzie kilku pracowników czeka na nowe wiadomości. Pracownicy ci tworzą faktury w formacie PDF i wysyłają je do odpowiednich użytkowników.
@Service
class BillingService {

    @Autowired
    private RabbitTemplate rabbitTemplate;

     public void bill(User user, Plan plan) {
        Invoice invoice = createInvoice(user, plan);
        // преобразует счет, например, в json и использует его Jak тело wiadomości
        rabbitTemplate.convertAndSend(exchange, routingkey, invoice);
        // ...
    }
}
Potencjalne błędy wyglądają teraz nieco inaczej, ponieważ nie otrzymujesz już natychmiastowych odpowiedzi OK ani BŁĄD, tak jak w przypadku synchronicznego połączenia HTTP. Zamiast tego możemy mieć trzy potencjalne scenariusze, które mogą się nie udać, co może rodzić następujące pytania:
  1. Czy moja wiadomość została dostarczona i wykorzystana przez pracownika? A może jest stracone? (Użytkownik nie otrzymuje faktury).
  2. Czy moja wiadomość została dostarczona tylko raz? Lub dostarczone więcej niż raz i przetworzone tylko raz? (Użytkownik otrzyma wiele faktur).
  3. Konfiguracja: od „Czy użyłem prawidłowych kluczy/nazw routingu dla giełdy” do „Czy mój broker komunikatów jest poprawnie skonfigurowany i utrzymywany lub czy jego kolejki są pełne?” (Użytkownik nie otrzymuje faktury).
Szczegółowy opis każdego indywidualnego wzorca odporności asynchronicznej mikrousługi wykracza poza zakres tego przewodnika. Istnieją jednak znaki wskazujące właściwy kierunek. Co więcej, będą one zależne od technologii przesyłania wiadomości. Przykłady:
  • Jeśli używasz implementacji JMS, takich jak ActiveMQ, możesz zamienić prędkość na gwarancję zatwierdzeń dwufazowych (XA).
  • Jeśli używasz RabbitMQ, przeczytaj najpierw ten samouczek, a następnie dokładnie zastanów się nad potwierdzeniami, odpornością na błędy i ogólnie niezawodnością komunikatów.
  • Być może ktoś jest dobrze zorientowany w konfiguracji serwerów Active lub RabbitMQ, zwłaszcza w połączeniu z klastrem i Dockerem (ktoś? ;))

Który framework byłby najlepszym rozwiązaniem dla mikroserwisów Java?

Z jednej strony można zainstalować bardzo popularną opcję taką jak Spring Boot . Bardzo ułatwia tworzenie plików .jar, ma wbudowany serwer WWW, taki jak Tomcat lub Jetty, i można go uruchomić szybko i wszędzie. Idealny do tworzenia aplikacji mikroserwisowych. Niedawno pojawiła się para wyspecjalizowanych frameworków mikrousługowych, Kubernetes lub GraalVM , częściowo inspirowanych programowaniem reaktywnym. Oto kilku bardziej interesujących pretendentów: Quarkus , Micronaut , Vert.x , Helidon . Ostatecznie będziesz musiał wybrać sam, ale możemy dać Ci kilka zaleceń, które mogą nie być całkowicie standardowe: Z wyjątkiem Spring Boot, wszystkie frameworki mikrousług są zwykle sprzedawane jako niewiarygodnie szybkie, z niemal natychmiastowym uruchamianiem , niewielkie zużycie pamięci i możliwość skalowania do nieskończoności. Materiały marketingowe zazwyczaj zawierają imponującą grafikę, która przedstawia platformę obok gigantycznego Spring Boota lub siebie nawzajem. W teorii oszczędza to nerwy programistom obsługującym starsze projekty, których załadowanie czasami zajmuje kilka minut. Lub programistów pracujących w chmurze, którzy chcą uruchomić/zatrzymać tyle mikrokontenerów, ile aktualnie potrzebują, w ciągu 50 ms. Przewodnik po mikrousługach Java.  Część 3: pytania ogólne - 3Problem polega jednak na tym, że te (sztuczne) czasy rozruchu i ponownego wdrożenia w niewielkim stopniu przyczyniają się do ogólnego sukcesu projektu. Przynajmniej mają one znacznie mniejszy wpływ niż silna infrastruktura frameworkowa, silna dokumentacja, społeczność i silne umiejętności programistów. Lepiej więc spojrzeć na to w ten sposób: Jeśli do tej pory:
  • Pozwalasz, aby Twoje ORMy działały szaleńczo, generując setki zapytań dla prostych przepływów pracy.
  • Do uruchomienia średnio złożonego monolitu potrzebujesz nieskończonych gigabajtów.
  • Masz tak dużo kodu, a złożoność jest tak duża (nie mówimy teraz o potencjalnie wolnych startach, takich jak Hibernacja), że załadowanie aplikacji zajmuje kilka minut.
W takim przypadku dodanie dodatkowych problemów z mycoservice (odporność sieci, przesyłanie wiadomości, DevOps, infrastruktura) będzie miało znacznie większy wpływ na Twój projekt niż ładowanie pustego Hello, world. A w przypadku ponownego wdrożenia w trakcie programowania możesz skorzystać z rozwiązań takich jak JRebel lub DCEVM . Poświęćmy chwilę, aby ponownie zacytować Simona Browna : „ Jeśli ludzie nie potrafią budować (szybkich i wydajnych) monolitów, trudno będzie im zbudować (szybkie i wydajne) mikrousługi, niezależnie od struktury ”. Wybieraj więc frameworki mądrze.

Które biblioteki są najlepsze do synchronicznych wywołań Java REST?

Z technicznego punktu widzenia prawdopodobnie otrzymasz jedną z następujących bibliotek klienta HTTP: natywna Java HttpClient (od Java 11), HttpClient Apache lub OkHttp . Zauważ, że mówię tutaj „prawdopodobnie”, ponieważ istnieją inne opcje, od starych, dobrych klientów JAX-RS po nowoczesnych klientów WebSocket . W każdym razie panuje tendencja do generowania klienta HTTP i odchodzenia od samodzielnego majstrowania przy wywołaniach HTTP. Aby to zrobić, musisz zapoznać się z projektem OpenFeign i jego dokumentacją jako punktem wyjścia do dalszej lektury.

Jacy są najlepsi brokerzy do asynchronicznego przesyłania komunikatów w języku Java?

Najprawdopodobniej natkniesz się na popularne ActiveMQ (Classic lub Artemis) , RabbitMQ lub Kafka .
  • ActiveMQ i RabbitMQ to tradycyjni, pełnoprawni brokerzy komunikatów. Obejmują interakcję „inteligentnego brokera” i „głupich użytkowników”.
  • Historycznie rzecz biorąc, ActiveMQ miał tę zaletę, że umożliwiał łatwe wstawianie (do testowania), co można złagodzić za pomocą ustawień RabbitMQ/Docker/TestContainer.
  • Kafki nie można nazwać tradycyjnym „inteligentnym” brokerem. Zamiast tego jest to stosunkowo „głupi” magazyn wiadomości (plik dziennika), który wymaga przetworzenia przez inteligentnych konsumentów.
Aby lepiej zrozumieć, kiedy używać RabbitMQ (lub ogólnie innych tradycyjnych brokerów komunikatów) lub Kafki, spójrz na ten kluczowy post jako punkt wyjścia. Ogólnie rzecz biorąc, wybierając brokera przesyłania wiadomości, staraj się ignorować sztuczne powody związane z wydajnością. Był czas, kiedy zespoły i społeczności internetowe nieustannie kłóciły się o to, jak szybki jest RabbitMQ i jak wolny jest ActiveMQ. Teraz te same argumenty są wysuwane w odniesieniu do RabbitMQ, mówią, że działa powoli przy 20-30 tysiącach wiadomości na sekundę. Kafka rejestruje 100 tysięcy wiadomości na sekundę. Szczerze mówiąc, takie porównania są jak porównywanie ciepłego z miękkim. Dodatkowo w obu przypadkach wartości przepustowości mogą mieścić się w niskim lub średnim przedziale, powiedzmy, Alibaba Group. Jednak jest mało prawdopodobne, że w rzeczywistości spotkałeś się z projektami tej skali (miliony wiadomości na minutę). Na pewno istnieją i mieliby problemy. W przeciwieństwie do pozostałych 99% „zwykłych” projektów biznesowych w języku Java. Więc nie zwracaj uwagi na modę i szum. Wybierz mądrze.

Jakich bibliotek mogę używać do testowania mikroserwisów?

To zależy od twojego stosu. Jeśli masz wdrożony ekosystem Spring, rozsądnie byłoby użyć specyficznych narzędzi frameworka . Jeśli JavaEE jest czymś w rodzaju Arquillian . Może warto rzucić okiem na Dockera i naprawdę dobrą bibliotekę Testcontainers , która pomaga w szczególności łatwo i szybko skonfigurować bazę danych Oracle na potrzeby lokalnego rozwoju lub testów integracyjnych. Aby przetestować próbne całe serwery HTTP, sprawdź Wiremock . Aby przetestować przesyłanie wiadomości asynchronicznych, spróbuj zaimplementować ActiveMQ lub RabbitMQ, a następnie napisać testy przy użyciu Awaitility DSL . Ponadto używane są wszystkie zwykłe narzędzia - Junit , TestNG dla AssertJ i Mockito . Należy pamiętać, że nie jest to pełna lista. Jeśli nie znajdziesz tutaj swojego ulubionego narzędzia, opublikuj je w sekcji komentarzy.

Jak włączyć rejestrowanie dla wszystkich mikrousług Java?

Logowanie w przypadku mikroserwisów to temat ciekawy i dość złożony. Zamiast mieć jeden plik dziennika, którym można manipulować za pomocą poleceń less lub grep, masz teraz n plików dziennika i nie chcesz, aby były zbyt rozproszone. Cechy ekosystemu pozyskiwania drewna są dobrze opisane w tym artykule (w języku angielskim). Koniecznie przeczytaj i zwróć uwagę na sekcję Scentralizowane logowanie z perspektywy mikroserwisów . W praktyce można spotkać się z różnymi podejściami: Administrator systemu pisze określone skrypty, które zbierają i łączą pliki dziennika z różnych serwerów w jeden plik dziennika i umieszczają je na serwerach FTP w celu pobrania. Uruchamianie kombinacji cat/grep/unig/sort w równoległych sesjach SSH. Dokładnie to robi Amazon AWS i możesz poinformować o tym swojego menedżera. Użyj narzędzia takiego jak Graylog lub ELK Stack (Elasticsearch, Logstash, Kibana)

Jak moje mikrousługi odnajdują się nawzajem?

Do tej pory zakładaliśmy, że nasze mikroserwisy wiedzą o sobie i znają odpowiadający im IPS. Porozmawiajmy o konfiguracji statycznej. Zatem nasz monolit bankowy [ip = 192.168.200.1] wie, że musi komunikować się z serwerem ryzyka [ip = 192.168.200.2], który jest zakodowany na stałe w pliku właściwości. Możesz jednak sprawić, że wszystko będzie bardziej dynamiczne:
  • Użyj serwera konfiguracji opartego na chmurze, z którego wszystkie mikrousługi pobierają swoje konfiguracje, zamiast wdrażać pliki application.properties w swoich mikrousługach.
  • Ponieważ instancje usług mogą dynamicznie zmieniać swoją lokalizację, warto przyjrzeć się usługom, które wiedzą, gdzie znajdują się Twoje usługi, jakie są ich adresy IP i jak je trasować.
  • Teraz, gdy wszystko jest dynamiczne, pojawiają się nowe problemy, takie jak automatyczny wybór lidera: kto jest mistrzem, który pracuje nad pewnymi zadaniami, aby na przykład nie przetwarzać ich dwukrotnie? Kto zastępuje lidera, gdy ten poniesie porażkę? Na jakiej podstawie następuje wymiana?
Ogólnie rzecz biorąc, nazywa się to orkiestracją mikrousług i jest to kolejny temat bez dna. Biblioteki takie jak Eureka czy Zookeeper próbują „rozwiązać” te problemy, pokazując, które usługi są dostępne. Z drugiej strony wprowadzają dodatkową złożoność. Zapytaj każdego, kto kiedykolwiek zainstalował ZooKeeper.

Jak zorganizować autoryzację i uwierzytelnianie przy użyciu mikroserwisów Java?

Ten temat również zasługuje na osobną opowieść. Ponownie, opcje obejmują zakodowane na stałe podstawowe uwierzytelnianie HTTPS z niestandardowymi strukturami bezpieczeństwa po uruchomienie instalacji Oauth2 z własnym serwerem autoryzacji.

Jak mogę się upewnić, że wszystkie moje środowiska wyglądają tak samo?

To, co dotyczy wdrożeń bez mikrousługi, dotyczy również wdrożeń z mikrousługą. Wypróbuj kombinację Docker/Testcontainers i Scripting/Ansible.

Brak pytań: krótko o YAML

Odejdźmy na chwilę od bibliotek i zagadnień z nimi związanych i rzućmy okiem na Yaml. Ten format pliku jest de facto używany jako format „zapisywania konfiguracji jako kodu”. Używają go także proste narzędzia, takie jak Ansible i giganci, jak Kubernetes. Aby doświadczyć bólu związanego z wcięciami YAML, spróbuj napisać prosty plik Ansible i zobacz, jak bardzo musisz go edytować, zanim zacznie działać zgodnie z oczekiwaniami. I to pomimo formatu obsługiwanego przez wszystkie główne IDE! Następnie wróć, aby dokończyć czytanie tego przewodnika.
Yaml:
  - is:
    - so
    - great

A co z transakcjami rozproszonymi? Test wydajności? Inne tematy?

Może kiedyś, w przyszłych wydaniach podręcznika. Na razie to wszystko. Zostań z nami!

Problemy koncepcyjne z mikroserwisami

Oprócz specyficznych problemów związanych z mikrousługami w Javie istnieją inne problemy, powiedzmy, takie, które pojawiają się w każdym projekcie mikrousług. Dotyczą one przede wszystkim organizacji, zespołu i zarządzania.

Niedopasowanie frontendu i backendu

Niedopasowanie frontendu i backendu jest bardzo częstym problemem w wielu projektach mikroserwisowych. Co to znaczy? Tyle że w starych dobrych monolitach twórcy interfejsów WWW mieli jedno konkretne źródło pozyskiwania danych. W projektach mikroserwisowych programiści frontendowi nagle mają n źródeł, z których mogą pozyskiwać dane. Wyobraź sobie, że tworzysz jakiś projekt mikrousług IoT (Internet of Things) w Javie. Załóżmy, że zarządzasz maszynami geodezyjnymi i piecami przemysłowymi w całej Europie. Te piekarniki regularnie wysyłają aktualizacje dotyczące temperatur i tym podobnych. Wcześniej czy później możesz chcieć znaleźć piekarniki w interfejsie administratora, być może korzystając z mikrousług „wyszukiwania pieców”. W zależności od tego, jak rygorystycznie odpowiednicy backendu stosują się do przepisów dotyczących projektowania opartego na domenie lub mikrousług, mikrousługa „znajdź piekarnik” może zwracać tylko identyfikatory piekarnika, a nie inne dane, takie jak typ, model czy lokalizacja. Aby to zrobić, programiści frontendowi będą musieli wykonać jedno lub n dodatkowych wywołań (w zależności od implementacji stronicowania) w mikroserwisie „pobierz dane pieca” z identyfikatorami, które otrzymali z pierwszej mikrousługi. Przewodnik po mikrousługach Java.  Część 3: pytania ogólne - 4I chociaż jest to tylko prosty przykład, choć zaczerpnięty z prawdziwego (!) projektu, to jednak pokazuje on następujący problem: supermarkety stały się niezwykle popularne. To dlatego, że dzięki nim nie musisz udawać się do 10 różnych miejsc, aby kupić warzywa, lemoniadę, mrożoną pizzę i papier toaletowy. Zamiast tego jedziesz w jedno miejsce, tak jest łatwiej i szybciej. To samo dotyczy programistów front-end i mikroserwisów.

Oczekiwania kierownictwa

Kierownictwo ma błędne wrażenie, że teraz musi zatrudnić nieskończoną liczbę programistów do (nadrzędnego) projektu, ponieważ programiści mogą teraz pracować całkowicie niezależnie od siebie, każdy na własnym mikroserwisie. Na samym końcu (na krótko przed uruchomieniem) wymagana jest jedynie niewielka praca integracyjna. Przewodnik po mikrousługach Java.  Część 3: pytania ogólne – 5W rzeczywistości takie podejście jest niezwykle problematyczne. W kolejnych akapitach postaramy się wyjaśnić dlaczego.

„Mniejsze kawałki” nie oznaczają „lepszych kawałków”

Dużym błędem byłoby zakładać, że kod podzielony na 20 części będzie z konieczności wyższej jakości niż jeden cały fragment. Nawet jeśli spojrzymy na jakość z czysto technicznego punktu widzenia, w naszych poszczególnych usługach może nadal działać 400 zapytań Hibernate w celu wybrania użytkownika z bazy danych, przechodząc przez warstwy nieobsługiwanego kodu. Jeszcze raz wracamy do cytatu Simona Browna: jeśli nie zbudujesz poprawnie monolitów, trudno będzie zbudować odpowiednie mikroserwisy. Często jest już bardzo późno, aby mówić o odporności na błędy w projektach mikroserwisowych. Do tego stopnia, że ​​czasami aż strach zobaczyć, jak mikroserwisy sprawdzają się w rzeczywistych projektach. Powodem tego jest to, że programiści Java nie zawsze są gotowi studiować tolerancję błędów, sieci i inne powiązane tematy na odpowiednim poziomie. Same „elementy” są mniejsze, ale „części techniczne” są większe. Wyobraź sobie, że Twój zespół ds. mikrousług zostaje poproszony o napisanie technicznej mikrousługi umożliwiającej logowanie do systemu baz danych, na przykład takiej:
@Controller
class LoginController {
    // ...
    @PostMapping("/login")
    public boolean login(String username, String password) {
        User user = userDao.findByUserName(username);
        if (user == null) {
            // обработка варианта с несуществующим пользователем
            return false;
        }
        if (!user.getPassword().equals(hashed(password))) {
            // обработка неверного пароля
            return false;
        }
        // 'Ю-ху, залогинLubсь!';
        // установите cookies, делайте, что угодно
        return true;
    }
}
Teraz Twój zespół może zdecydować (a może nawet przekonać ludzi biznesu), że jest to zbyt proste i nudne, zamiast pisać usługę logowania, lepiej napisać naprawdę użyteczną mikrousługę UserStateChanged bez żadnych realnych i wymiernych implikacji biznesowych. A ponieważ niektórzy obecnie traktują Javę jak dinozaura, napiszmy nasz mikroserwis UserStateChanged w modnym Erlangu. A spróbujmy gdzieś wykorzystać czerwono-czarne drzewa, bo Steve Yegge napisał, że trzeba je znać na wylot, żeby aplikować do Google. Z punktu widzenia integracji, konserwacji i ogólnego projektu jest to tak samo złe, jak pisanie warstw kodu spaghetti w jednym monolicie. Sztuczny i zwyczajny przykład? To prawda. Może się to jednak zdarzyć w rzeczywistości.

Mniej elementów - mniej zrozumienia

Wtedy naturalnie pojawia się pytanie o zrozumienie systemu jako całości, jego procesów i przepływów pracy, ale jednocześnie Ty, jako programista, jesteś odpowiedzialny tylko za pracę nad swoim wyizolowanym mikroserwisem [95: login-101: updateUserProfile]. Harmonizuje to z poprzednim akapitem, ale w zależności od Twojej organizacji, poziomu zaufania i komunikacji może to prowadzić do wielu zamieszania, wzruszeń ramionami i obwiniania, jeśli dojdzie do przypadkowej awarii w łańcuchu mikrousług. I nie ma nikogo, kto wziąłby pełną odpowiedzialność za to, co się stało. I wcale nie jest to kwestia nieuczciwości. Tak naprawdę bardzo trudno jest połączyć różne części i zrozumieć ich miejsce w ogólnym obrazie projektu.

Komunikacja i obsługa

Poziom komunikacji i obsługi zależy w dużej mierze od wielkości firmy. Jednak ogólna zależność jest oczywista: im więcej, tym bardziej problematyczne.
  • Kto prowadzi mikroserwis nr 47?
  • Czy właśnie wdrożyli nową, niezgodną wersję mikrousługi? Gdzie to zostało udokumentowane?
  • Z kim muszę porozmawiać, aby poprosić o nową funkcję?
  • Kto będzie wspierał ten mikroserwis w Erlangu, po tym jak jedyny znający ten język odszedł z firmy?
  • Wszystkie nasze zespoły mikroserwisowe pracują nie tylko w różnych językach programowania, ale także w różnych strefach czasowych! Jak to wszystko poprawnie skoordynować?
Przewodnik po mikrousługach Java.  Część 3: pytania ogólne - 6Najważniejsze jest to, że podobnie jak w przypadku DevOps, pełne podejście do mikroserwisów w dużej, być może nawet międzynarodowej firmie, wiąże się z szeregiem dodatkowych problemów komunikacyjnych. A firma musi się do tego poważnie przygotować.

wnioski

Po przeczytaniu tego artykułu można pomyśleć, że jego autor jest zagorzałym przeciwnikiem mikroserwisów. Nie do końca jest to prawdą – staram się w zasadzie wskazać punkty, na które w szalonym wyścigu po nowe technologie mało kto zwraca uwagę.

Mikrousługi czy monolit?

Korzystanie z mikrousług Java w dowolnym miejscu i czasie to skrajność. Drugi okazuje się być czymś w rodzaju setek dobrych, starych modułów Mavena w monolicie. Twoim zadaniem jest znalezienie właściwej równowagi. Dotyczy to szczególnie nowych projektów. Nic nie stoi na przeszkodzie, aby przyjąć bardziej konserwatywne, „monolityczne” podejście i stworzyć mniej dobrych modułów Mavena, zamiast zaczynać od dwudziestu mikrousług gotowych do pracy w chmurze.

Mikrousługi generują dodatkową złożoność

Pamiętaj, że im więcej masz mikrousług i im słabszy DevOps masz (nie, uruchomienie kilku skryptów Ansible lub wdrożenie w Heroku się nie liczy!), tym więcej problemów będziesz mieć w dalszej części procesu. Nawet samo przeczytanie do końca sekcji tego przewodnika poświęconej ogólnym pytaniom dotyczącym mikroserwisów Java jest dość żmudnym zadaniem. Pomyśl intensywnie o wdrożeniu rozwiązań wszystkich problemów z infrastrukturą, a nagle zdasz sobie sprawę, że nie chodzi już tylko o programowanie biznesowe (za co ci płacą), ale raczej o ulepszanie większej liczby technologii w jeszcze większej liczbie technologii. Shiva Prasad Reddy doskonale podsumował to na swoim blogu : „Nie masz pojęcia, jakie to okropne, gdy zespół spędza 70% czasu na zmaganiu się z nowoczesną infrastrukturą, a tylko 30% czasu pozostaje na realizację właściwej logiki biznesowej. „ Śiwa Prasad Reddy

Czy warto tworzyć mikroserwisy Java?

Aby odpowiedzieć na to pytanie, chciałbym zakończyć ten artykuł bardzo bezczelnym zwiastunem przypominającym wywiad z Google. Jeśli znasz odpowiedź na to pytanie z doświadczenia, nawet jeśli wydaje się, że nie ma ona nic wspólnego z mikrousługami, możesz być gotowy na podejście oparte na mikrousługach.

Scenariusz

Wyobraź sobie, że masz monolit Java działający samodzielnie na najmniejszym serwerze dedykowanym firmy Hetzner . To samo dotyczy Twojego serwera bazy danych, działa on również na podobnej maszynie Hetznera . Załóżmy także, że monolit Java może obsługiwać przepływy pracy, powiedzmy rejestrację użytkownika, i nie tworzysz setek zapytań do bazy danych na przepływ pracy, ale bardziej rozsądną liczbę (<10).

Pytanie

Ile połączeń z bazą danych powinien otwierać monolit Java (pula połączeń) na serwerze bazy danych? Dlaczego? Jak myślisz, ilu jednocześnie aktywnych użytkowników może (w przybliżeniu) skalować Twój monolit?

Odpowiedź

Zostaw odpowiedź na te pytania w sekcji komentarzy. Czekam z niecierpliwością na wszystkie odpowiedzi. Przewodnik po mikrousługach Java.  Część 3: pytania ogólne - 8Teraz zdecyduj. Jeśli przeczytałeś do samego końca, jesteśmy Ci bardzo wdzięczni!
Komentarze
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION