Komunikacja między lokalnymi systemami JVMs

Moje pytanie: Jakie podejście powinienem/powinnam zastosować, aby komunikować się między dwoma lub więcej instancjami JVM, które działają lokalnie?

Jakiś opis problemu:
Rozwijam system dla projektu, który wymaga osobnych instancji JVM, aby całkowicie odizolować pewne zadania od siebie.

Gdy jest uruchomiony, JVM 'rodzic ' utworzy' potomne ' JVM, które będzie oczekiwał wykonania, a następnie zwróci do niego wyniki (w formacie stosunkowo prostego POJO klasy, A może strukturyzowane dane XML). Wyniki te nie powinny być przekazywane za pomocą rur SysErr/SysOut/sysin, ponieważ dziecko może już z nich korzystać w ramach swojego działania.

Jeśli dziecko JVM nie odpowie wynikami w określonym czasie, rodzic JVM powinien być w stanie zasygnalizować dziecku zaprzestanie przetwarzania lub zabić proces potomny. W przeciwnym razie dziecko JVM powinno normalnie wyjść po zakończeniu zadania.

Dotychczasowe badania:
Wiem. istnieje wiele technologii, które mogą być użyte np....

  • Korzystanie z biblioteki RMI Javy
  • używanie gniazd do przesyłania obiektów
  • Korzystanie z bibliotek dystrybucyjnych, takich jak Cajo, Hessian

...ale jestem zainteresowany słuchaniem, co podejścia inni mogą rozważyć przed realizacją jednej z tych opcji, lub innych.

Dzięki za pomoc lub Radę w tym zakresie!

Edycje:
ilość danych do przesłania - stosunkowo mała, to w większości będzie to tylko garść Pojo zawierających ciągi znaków, które będą reprezentować wynik wykonania przez dziecko. Jeśli jakiekolwiek rozwiązanie byłoby nieefektywne na większych ilościach informacji, jest to mało prawdopodobne , aby być problemem w moim systemie. Przekazywana kwota powinna być dość statyczna, a więc to nie , a nie musi być skalowalne.

Opóźnienie transferu- nie jest w tym przypadku krytycznym problemem, chociaż jeśli potrzebne jest jakiekolwiek "badanie" wyników, powinno to być w stanie aby być dość częstym bez znaczących kosztów ogólnych, więc mogę utrzymać responsywny GUI na górze w późniejszym czasie (np.]}

Author: obfuscation, 2011-02-19

11 answers

Użyłbym KryoNet z lokalnymi gniazdami, ponieważ specjalizuje się w serializacji i jest dość lekki (dostajesz również zdalne wywołanie metody! Używam go teraz), ale wyłącz limit czasu rozłączania gniazda.

RMI zasadniczo działa na zasadzie, że masz typ zdalny i że typ zdalny implementuje interfejs. Ten interfejs jest współdzielony. Na komputerze lokalnym interfejs można powiązać za pomocą biblioteki RMI do kodu "injected" w pamięci z RMI Biblioteka, w wyniku czego masz coś, co spełnia interfejs, ale jest w stanie komunikować się ze zdalnym obiektem.

 5
Author: Chris Dennett,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-19 18:03:17

Nie bezpośrednio odpowiedź na twoje pytanie, ale sugestia alternatywy. Czy rozważałeś OSGI ?

Pozwala na uruchamianie projektów java w całkowitej izolacji od siebie, w ramach tego samego jvm. Piękno tego polega na tym, że komunikacja między projektami jest bardzo łatwa dzięki usługom (zobacz podstawowe specyfikacje PDF strona 123). W ten sposób nie odbywa się" serializacja " żadnego rodzaju, ponieważ Dane i połączenia są w tym samym jvm.

Ponadto wszystkie Twoje wymagania jakości usług (Czas reakcji itp...) odejdź - musisz się tylko martwić o to, czy usługa jest w górę czy w dół w momencie, gdy chcesz z niej korzystać. I do tego masz naprawdę ładną specyfikację, która robi to dla Ciebie, nazywając usługi deklaratywne (Zobacz Enterprise Spec PDF strona 141)

Przepraszam za odpowiedź off-topic, ale pomyślałem, że inni ludzie mogą rozważyć to jako alternatywę.

Update

Aby odpowiedzieć na twoje pytanie o Ochrona, nigdy nie rozważałem takiego scenariusza. Nie wierzę, że istnieje sposób, aby wymusić użycie "pamięci" w OSGI.

Istnieje jednak sposób komunikacji poza JVM pomiędzy różnymi środowiskami URUCHOMIENIOWYMI OSGI. Nazywa się to usługami zdalnymi (patrz Enterprise Spec PDF, Strona 7). Mają tam również przyjemną dyskusję na temat czynników, które należy wziąć pod uwagę przy robieniu czegoś takiego(patrz 13.1 błędy).

Ludzie w Apache Felix (implementacja OSGI) myślę, że mają implementacja tego z ipojo, o nazwie Distributed Services with Ipojo (ich opakowanie, aby ułatwić korzystanie z usług). Nigdy tego nie używałem - więc zignoruj mnie, jeśli się mylę.

 6
Author: drozzy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-20 01:19:30

Akka jest inną opcją, podobnie jak inne frameworki java actor, zapewnia komunikację i inne gadżety wywodzące się z modelu actor.

 5
Author: superfav,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-19 21:12:07

Jeśli nie możesz używać stdin/stdout, to wybrałbym gniazda. Potrzebujesz jakiejś warstwy serializacyjnej na wierzchu gniazd (tak jak w przypadku stdin/stdout), a RMI jest bardzo łatwą w użyciu i dość skuteczną warstwą.

Jeśli użyłeś RMI i stwierdziłeś, że wydajność nie jest wystarczająco dobra, przełączyłbym się na jakiś bardziej wydajny serializer - jest Wiele opcji.

Nie zbliżałbym się do web services czy XML. To wygląda na kompletną stratę czasu, prawdopodobnie wziąć większy wysiłek i mniejsza wydajność niż RMI.

 4
Author: Tom Anderson,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-19 17:59:59

Niewiele osób już lubi RMI.

Opcje:

  1. Usługi Internetowe. np. http://cxf.apache.org
  2. JMX. Jest to naprawdę sposób użycia RMI pod stołem, ale to by zadziałało.
  3. inne protokoły IPC; cytowałeś Hessian
  4. Roll-your-own przy użyciu gniazd, lub nawet pamięci współdzielonej. (Otwórz zmapowany plik w rodzicu, otwórz go ponownie w dziecku. Nadal potrzebujesz czegoś do synchronizacji.)

Przykładami uwag są Apache ant (który rozwidla wszystkie rodzaje Jvms w tym czy innym celu), Apache maven i wariant open source tanukisoft daemonization kit.

Osobiście bardzo lubię serwisy internetowe, więc to właśnie młotek, który zwykle zamieniam w gwoździe. Typowa usługa JAX-WS+JAX-B lub JAX-RS+JAX-B jest bardzo mało kodu z CXF i zarządza dla mnie całą serializacją i deserializacją danych.

 3
Author: bmargulies,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-19 20:08:44

To było wspomniane powyżej, ale chciałem nieco rozszerzyć sugestię JMX. właściwie robimy prawie dokładnie to, co planujesz zrobić (z tego, co mogę wyciągnąć z Twoich różnych komentarzy). wylądowaliśmy na JMX z różnych powodów, z których kilka wspomnę tutaj. po pierwsze, JMX polega na zarządzaniu, więc ogólnie jest idealnym rozwiązaniem dla tego ,co chcesz robić (zwłaszcza jeśli planujesz już mieć Usługi jmx dla innych zadań zarządzania). każdy wysiłek, jaki włożysz do interfejsów jmx będzie podwójne zadanie jako API można wywołać za pomocą narzędzi zarządzania java, takich jak jvisualvm. to prowadzi do mojej następnej kwestii, która jest najbardziej istotna dla tego, czego chcesz. nowe Api Attachment w jdk 6 i wyżej jest bardzo słodkie. umożliwia dynamiczne wykrywanie i komunikowanie się z uruchomionymi systemami jvms. pozwala to na przykład na awarię i ponowne uruchomienie procesu" kontrolera " oraz ponowne odnalezienie wszystkich istniejących procesów roboczych. to zadatki na bardzo solidny system. to było wspomniano powyżej, że JMX zasadniczo rmi pod maską, jednak w przeciwieństwie do bezpośredniego korzystania z rmi, nie musisz zarządzać wszystkimi szczegółami połączenia (np. radzenie sobie z unikalnymi portami, wykrywalność itp.). Dołącz api jest trochę ukrytym klejnotem w jdk, ponieważ nie jest zbyt dobrze udokumentowane. kiedy na początku grzebałem w tych rzeczach, nie znałem nazwy api, więc zastanawianie się, jak działa "magia" w jvisualvm i jconsole, było bardzo trudne. w końcu natknąłem się na artykuł typu Ten jeden , który pokazuje, jak w rzeczywistości używać Dołącz api dynamicznie we własnym programie.

 3
Author: jtahlborn,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-08-03 02:14:56

Chociaż jest przeznaczony do potencjalnie zdalnej komunikacji między JVM, myślę, że przekonasz się, że Netty działa bardzo dobrze między lokalnymi instancjami JVM.

Jest to prawdopodobnie najbardziej wydajna / solidna / szeroko obsługiwana biblioteka tego typu dla Javy.

 2
Author: mikera,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-19 18:12:30

Wiele jest omówionych powyżej. Ale czy to gniazd, rmi, jms - jest lof brudnej roboty. Ja bym doradził akka . Jest to model oparty na aktorze, który komunikuje się ze sobą za pomocą wiadomości.

Piękne jest to, że aktorzy mogą być na tym samym JVM lub innym (bardzo mało config), a akka zajmie się resztą za Ciebie. Nie widziałem bardziej czystszego sposobu niż to:)

 2
Author: Jatin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-05-09 09:23:09

Wypróbuj jGroups Jeśli dane do przekazania nie są ogromne.

 1
Author: zengr,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-19 18:01:42
 0
Author: Felix Ng,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-02-19 19:40:41

Jak już wspomniałeś, możesz oczywiście wysyłać obiekty przez sieć, ale jest to kosztowne, nie wspominając o uruchomieniu oddzielnego JVM.

Innym podejściem, jeśli chcesz po prostu oddzielić różne światy wewnątrz jednego JVM, jest ładowanie klas za pomocą różnych classloaderów. ClassA @ CL1!= ClassA@CL2 jeśli są ładowane przez CL1 i CL2 jako classloadery.

Aby włączyć komunikację pomiędzy classA @ CL1 i classA@CL2 można mieć trzy classloadery.

  • CL1 że ładuje proces1
  • CL2, który ładuje process2 (te same klasy co w CL1)
  • CL3 ładujący klasy komunikacyjne (Pojo i Service).

Teraz niech CL3 będzie nadrzędnym classloaderem CL1 i CL2.

W klasach ładowanych przez CL3 możesz mieć lekką funkcję wysyłania/odbierania komunikacji (send(Pojo) / receive(Pojo)) pomiędzy klasami w CL1 i klasami w CL2.

W CL3 wystawiasz statyczną usługę, która umożliwia implementacje z CL1 i CL2 Zarejestruj się, aby wysyłać i odbierać Pojo.

 0
Author: Niclas,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-04-25 21:55:37