Jestem stosunkowo nowy w architekturze mikrousług. Mamy aplikację internetową o średniej wielkości i rozważam zalety i wady podziału jej na mikrousługi zamiast monolitycznego systemu, który teraz rozwijamy.
O ile dobrze rozumiem, rozważyć microservices A
i B
każdy z nich polegają na podzbiór danych, że druga. Jeśli wiadomość zostanie opublikowana z A
informacją, że coś się zmieniło, B
może zużyć tę wiadomość i powielić lokalną kopię A
informacji i użyć go do zrobienia tego, co B
trzeba.
Jednak co się stanie, jeśli nastąpi B
awaria / awaria, a po chwili wróci ponownie. W tym czasie A
opublikował jeszcze dwie wiadomości. Skąd B
wiadomo, jak zaktualizować lokalną kopię A
informacji?
Oczywiście, jeśli B
jest jedynym konsumentem w A
kolejce, to może zacząć ją czytać po powrocie do trybu online, ale co, jeśli są inni konsumenci w kolejce i te wiadomości są konsumowane?
Bardziej konkretnym przykładem jest to, że jeśli Users
usługa ma zaktualizowany adres e-mail, gdy Billing
mikrousługa jest wyłączona, jeśli Billing
mikrousługa wróci ponownie, skąd wiadomo, że wiadomość e-mail została zaktualizowana?
Kiedy mikrousługi pojawiają się ponownie, czy nadają, mówiąc: „Hej, wróciłem, podaj mi wszystkie swoje aktualne informacje?”
Ogólnie, jakie byłyby najlepsze praktyki branżowe w zakresie synchronizacji danych?
źródło
Orders
trzeba coś wiedziećUsers
?Odpowiedzi:
Zakwestionowałbym cały twój pomysł „wypychania danych do wszystkich innych mikrousług”.
Zwykle, jeśli usługa rozliczeniowa potrzebuje adresu e-mail, po prostu prosi usługę adresową o adres e-mail konkretnego klienta. Nie musi przechowywać kopii wszystkich danych adresowych ani nie będzie informowany, jeśli coś się zmieni. Po prostu pyta i otrzymuje odpowiedź z najnowszych danych.
źródło
Po przeprowadzeniu nieco więcej badań natknąłem się na ten artykuł, z którego wyciągnąłem cytaty, które moim zdaniem są pomocne w tym, co chcę osiągnąć (i dla przyszłych czytelników). Umożliwia to przyjęcie modelu programowania reaktywnego zamiast modelu programowania imperatywnego.
Pozyskiwanie zdarzeń
Pomaga to w osiągnięciu tego, że jeśli mikrousługa ulegnie awarii, a inne związane z nią zdarzenia zostaną opublikowane, a zdarzenia zostaną zużyte przez, powiedzmy, inne przypadki tej mikrousługi, gdy ta mikrousługa powróci, może odnosić się do tego,
event store
aby pobrać wszystkie wydarzenia, które przeoczył w okresie upadku.Apache Kafka jako Broker wydarzeń
Rozważ zastosowanie Apache Kafka, który może przechowywać i wywoływać tysiące zdarzeń na sekundę oraz ma wbudowane mechanizmy replikacji i odporności na uszkodzenia. Ma trwały magazyn zdarzeń, które mogą być przechowywane na dysku w nieskończoność i zużyte w dowolnym momencie (ale nie usunięte) z Tematu (fantazyjna kolejka Kafki), do którego zostały dostarczone.
W rzeczywistości, kiedy konsumenci identyfikują się z Kafką, Kafka rejestruje, które wiadomości zostały dostarczone do którego konsumenta, aby nie mogła go ponownie podać.
Sagi
Właśnie wtedy pojawia się saga. Saga to sekwencja lokalnych transakcji. Każda transakcja lokalna aktualizuje bazę danych i publikuje komunikat lub zdarzenie w celu uruchomienia następnej transakcji lokalnej w sadze. Jeśli lokalna transakcja nie powiedzie się, ponieważ narusza regułę biznesową, saga wykonuje serię transakcji kompensacyjnych, które cofają zmiany wprowadzone w poprzednich transakcjach lokalnych. Przeczytaj to, aby uzyskać więcej informacji.
źródło
Nawet jeśli się spóźnię, postawiłbym swoje 2 centy na argument, ponieważ uważam, że jest to ważny punkt, gdy chcesz ocenić e zaprojektować architekturę mikrousług opartą na zdarzeniach. Każda mikrousługa dokładnie wie, które zdarzenia wpływają na jej stan i jest w stanie na nie czekać. Gdy mikrousługa nie jest dostępna, powinien istnieć komponent, który przechowuje wiadomości potrzebne z uszkodzonej mikrousługi, dopóki nie będzie w stanie ich „zużyć”. W rzeczywistości jest to model „producent / konsument”, a nie model „publikuj / subskrybuj”. Brokerzy wiadomości (jak Kafka, RabbitMQ, ActiveMQ itp.) Są zwykle najlepszym sposobem na osiągnięcie tego zachowania (chyba że nie wdrażasz czegoś innego, takiego jak pozyskiwanie zdarzeń), zapewniając trwałe kolejki i mechanizm potwierdzenia / nacka.
Teraz mikrousługa wie, że wiadomość jest ostatecznie dostarczana, ale to nie wystarczy: w jaki sposób oczekuje dostarczenia pojedynczej wiadomości? czy może zarządzać dostarczaniem wielu kopii tego samego powiadomienia o zdarzeniu? Jest to kwestia dostawy semantycznej (przynajmniej raz, dokładnie raz)
Końcowe przemyślenia):
Kiedy dodajesz mikrousługę do swojej architektury, która musi pobierać zdarzenia od innych, musisz wykonać pierwszą synchronizację
Nawet broker może zawieść, w tym przypadku wiadomości zostaną utracone
dla obu scenariuszy przydatne byłyby proste mechanizmy ponownego nawodnienia stanu mikrousług. Może to być interfejs API REST lub skrypt, który wysyła komunikaty, ale najważniejsze jest, aby mieć środki do wykonania jakiegoś zadania konserwacyjnego
źródło
Możesz zamienić normalną kolejkę zdarzeń na model wydawcy / subskrybenta, w którym
A
usługa publikuje nową wiadomość w temacie T, aB
typ mikrousług subskrybuje ten sam temat.Idealnie
B
byłaby to usługa bezstanowa i wykorzystywałaby odłączoną usługę trwałości, tak żeB
instancja usługi, która uległa awarii , zostałaby zastąpiona przez odrodzenie jednej lub więcejB
instancji usługi w celu kontynuowania pracy, odczytywanie z tej samej współużytkowanej usługi trwałości.źródło
Jeśli chcesz, aby B miał dostęp do wewnętrznych danych A, lepiej byłoby po prostu dać mu dostęp do wewnętrznych baz danych A.
Jednak nie powinieneś tego robić, cały punkt architektury zorientowanej na usługi polega na tym, że usługa B nie widzi stanu wewnętrznego usługi A i jest ograniczona do wysyłania żądań za pośrednictwem interfejsów API REST (i odwrotnie).
W twoim przypadku możesz mieć usługę danych użytkownika, która ma obowiązek przechowywania wszystkich danych użytkownika. Inne usługi, które chcą korzystać z tych danych, żądają ich tylko wtedy, gdy są potrzebne i nie przechowują kopii lokalnej (co przy okazji jest naprawdę przydatne, jeśli myślisz o zgodności z RODO). Usługa danych użytkownika może obsługiwać proste operacje CRUD, takie jak „Utwórz nowego użytkownika” lub „Zmień nazwę dla ID_użytkownika 23”, lub może mieć bardziej skomplikowane operacje, „Znajdź wszystkich standardowych użytkowników z datą urodzin w ciągu najbliższych 2 tygodni i daj im status premium premium ”. Teraz, gdy twoja usługa fakturowania musi wysłać wiadomość e-mail do użytkownika 42, zapyta usługę danych użytkownika „Jaki jest adres e-mail dla ID_użytkownika 42”, wykorzysta swoje dane wewnętrzne ze wszystkimi informacjami rozliczeniowymi do stworzenia wiadomości e-mail, a następnie może przekazać adres e-mail i treść do serwera pocztowego.
źródło