Jaka jest odpowiedź Haskella na węzeł.js?

Uważam, że społeczność Erlang nie zazdrości Node.js jak nie blokuje natywnie We / Wy i ma sposoby na łatwe skalowanie wdrożeń do więcej niż jednego procesora (coś nawet nie wbudowanego w węzeł.js). Więcej szczegółów na http://journal.dedasys.com/2010/04/29/erlang-vs-node-js I węzeł.js lub Erlang

A Haskell? Może Haskell zapewnić niektóre z zalet Node.js, czyli czyste rozwiązanie, aby uniknąć blokowania we/wy bez konieczności korzystania z wielu wątków programowanie?


Jest wiele rzeczy, które są atrakcyjne z Node.js

    [12]} zdarzenia: Brak manipulacji wątkiem, programista dostarcza tylko wywołania zwrotne (jak w frameworku Snap)
  1. wywołania zwrotne są gwarantowane w jednym wątku: nie ma możliwości warunku wyścigu.
  2. ładne i proste uniksowe API. Bonus: doskonała obsługa HTTP. Dostępny również DNS.
  3. każde wejście/wyjście jest domyślnie asynchroniczne. Ułatwia to unikanie zamków. Jednak za dużo Przetwarzanie CPU w wywołaniu zwrotnym wpłynie na inne połączenia(w tym przypadku zadanie powinno podzielić się na mniejsze podrzędne zadania i ponownie zaplanować).
  4. ten sam język po stronie klienta i po stronie serwera. (Nie widzę w tym jednak zbyt dużej wartości. jQuery i Node.js dzielą model programowania zdarzeń, ale reszta jest bardzo inna. Po prostu nie widzę, jak dzielenie kodu między serwerem a klientem może być przydatne w praktyce.)
  5. Wszystko to zapakowane w jeden produkt.
Author: Rakete1111, 2010-10-02

7 answers

Ok, więc po obejrzeniu trochę węzła.js presentation że @gawi wskazał mi, mogę powiedzieć trochę więcej o tym, jak Haskell porównuje do węzła.js. W prezentacji Ryan opisuje niektóre zalety zielonych wątków, ale dalej mówi, że brak abstrakcji wątku nie jest dla niego wadą. Nie zgadzam się z jego stanowiskiem, szczególnie w kontekście Haskella: myślę, że abstrakcje, które dostarczają wątki, są niezbędne do tworzenia kodu serwera łatwiejsze do uzyskania i bardziej wytrzymałe. W szczególności:

  • Użycie jednego wątku na jedno połączenie pozwala na napisanie kodu, który wyraża komunikację z jednym klientem, a nie kodu, który dotyczy wszystkich klientów w tym samym czasie. Pomyśl o tym w ten sposób: serwer obsługujący wielu klientów z wątkami wygląda prawie tak samo jak serwer obsługujący jednego klienta; główna różnica polega na tym, że gdzieś w tym pierwszym jest fork. Jeśli protokół jest implementacja jest w ogóle złożona, zarządzanie maszyną stanową dla wielu klientów jednocześnie staje się dość trudne, podczas gdy wątki pozwalają po prostu skryptować komunikację z jednym klientem. Kod jest łatwiejszy do uzyskania, a także łatwiejszy do zrozumienia i utrzymania.

  • Wywołania zwrotne na pojedynczym wątku OS to wielozadaniowość kooperacyjna, w przeciwieństwie do wielozadaniowości prewencyjnej, która jest tym, co dostajesz z wątkami. Główną wadą wielozadaniowości jest to, że programista jest odpowiedzialny za upewnienie się, że nie ma głodu. Traci modułowość: popełnić błąd w jednym miejscu, a może zepsuć cały system. Jest to naprawdę coś, o co nie chcesz się martwić, a uprzedzenie jest prostym rozwiązaniem. Co więcej, komunikacja między wywołaniami zwrotnymi nie jest możliwa(byłoby to niemożliwe).

  • Współbieżność nie jest trudna w Haskell, ponieważ większość kodu jest czysta, podobnie jak konstrukcja bezpieczna dla wątków. Istnieją proste prymitywy komunikacyjne. On znacznie trudniej strzelić sobie w stopę z użyciem Haskell niż w języku z nieograniczonymi skutkami ubocznymi.

 213
Author: Simon Marlow,
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
2010-10-04 20:01:40

Czy Haskell może zapewnić niektóre korzyści z Node.js, czyli czyste rozwiązanie, aby uniknąć blokowania I / O bez odwoływania się do programowania wielowątkowego?

Tak, w rzeczywistości zdarzenia i wątki są zunifikowane w Haskell.

  • możesz programować w jawnych lekkich wątkach (np. miliony wątków na jednym laptopie).
  • lub; można programować w stylu asynchronicznym, opartym na skalowalnym powiadamianiu o zdarzeniach.

Threads are actually zaimplementowane w kategoriach zdarzeń , i działają na wielu rdzeniach, z płynną migracją wątków, z udokumentowaną wydajnością i aplikacjami.

Np. dla

zbiory równoległe nbody na 32 rdzeniach

alt text

W Haskell masz zarówno wydarzenia, jak i wątki, a ponieważ wszystkie wydarzenia są pod maską.

Przeczytaj artykuł opisujący wdrożenie.

 154
Author: Don Stewart,
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-04-17 17:08:00

Po pierwsze, nie mam twojego poglądu, że węzeł.js robi dobrze, ujawniając te wszystkie wezwania. Kończysz pisząc swój program w CPS (continuation passing style) i myślę, że zadaniem kompilatora powinno być wykonanie tej transformacji.

Zdarzenia: Brak manipulacji wątkiem, programista dostarcza tylko wywołania zwrotne (jak w frameworku Snap)

Więc mając to na uwadze, możesz pisać za pomocą stylu asynchronicznego, jeśli chcesz, ale robiąc to, stracisz na pisanie w efektywnym stylu synchronicznym, z jednym wątkiem na żądanie. Haskell jest śmiesznie wydajny w kodowaniu synchronicznym, szczególnie w porównaniu z innymi językami. Wszystko jest pod spodem.

Wywołania zwrotne są gwarantowane w jednym wątku: nie ma możliwości warunku wyścigu.

Nadal możesz mieć stan rasy w node.js, ale to trudniejsze.

Każde żądanie jest w swoim własnym wątku. Kiedy piszesz kod, który ma komunikować się z innymi threads, to bardzo proste, aby to threadsafe dzięki Haskell współbieżności primitives.

Ładne i proste uniksowe API. Bonus: doskonała obsługa HTTP. Dostępny również DNS.

Zajrzyj do hackage i przekonaj się sam.

Każde wejście/wyjście jest domyślnie asynchroniczne(może to być czasem denerwujące). Ułatwia to unikanie zamków. Jednak zbyt duże przetwarzanie procesora w wywołaniu zwrotnym wpłynie na inne połączenia (w tym przypadku zadanie powinien podzielić się na mniejsze pod-zadania i ponownie zaplanowane).

Nie masz takich problemów, ghc rozdzieli Twoją pracę między prawdziwymi wątkami OS.

Ten sam język po stronie klienta i po stronie serwera. (Nie widzę w tym jednak zbyt dużej wartości. JQuery i Node.js dzielą model programowania zdarzeń, ale reszta jest bardzo inna. Po prostu nie widzę, jak dzielenie kodu między serwerem a klientem może być przydatne w praktyce.)

Haskell nie wygra proszę... prawda? Pomyśl jeszcze raz, http://www.haskell.org/haskellwiki/Haskell_in_web_browser .

Wszystko to zapakowane w jeden produkt.

Pobierz ghc, odpal cabal. Jest paczka dla każdej potrzeby.

 18
Author: dan_waterworth,
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-06-22 06:46:37

Ja osobiście widzę węzeł.js i programowanie z wywołaniami zwrotnymi jako niepotrzebnie niskopoziomowe i trochę nienaturalne. Dlaczego program z wywołań zwrotnych, gdy dobry runtime, takie jak ten znaleziony w GHC może obsługiwać wywołań zwrotnych dla Ciebie i zrobić to całkiem efektywnie?

W międzyczasie GHC runtime znacznie się poprawiło: teraz jest wyposażony w "nowy menedżer IO" o nazwie MIO gdzie "M" oznacza, jak sądzę, multicore. Opiera się na fundamentach istniejącego IO managera, a jego głównym celem jest przezwyciężenie przyczyną degradacji wydajności 4 + Rdzeni. Wyniki przedstawione w tym artykule są imponujące. Zobacz siebie:

Z Mio, realistyczne serwery HTTP w skali Haskella do 20 rdzeni procesora, osiągając maksymalną wydajność do 6,5 x w porównaniu do tych samych serwerów z poprzednimi wersjami GHC. Poprawiono także opóźnienie serwerów Haskell: [...] przy umiarkowanym obciążeniu zmniejsza oczekiwany czas reakcji o 5,7 x w porównaniu z poprzednimi wersjami GHC

I:

Pokazujemy również, że dzięki Mio, McNettle (kontroler SDN napisany w Haskell) może skutecznie skalować do ponad 40 rdzeni, osiągnąć przepustowość ponad 20 milionów nowych żądań na sekundę na jednej maszynie, a tym samym stać się najszybszym ze wszystkich istniejących kontrolerów SDN.

Mio doczekało się wydania GHC 7.8.1. Osobiście postrzegam to jako duży krok naprzód w wydajności Haskell. Bardzo interesujące byłoby porównanie istniejących aplikacji internetowych wydajność opracowana przez poprzednią wersję GHC i 7.8.1.

 8
Author: vlprans,
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-02-01 14:27:29

Pytanie jest dość śmieszne, ponieważ 1) Haskell rozwiązał już ten problem w znacznie lepszy sposób i 2) w mniej więcej taki sam sposób jak Erlang. Oto benchmark względem węzła: http://www.yesodweb.com/blog/2011/03/preliminary-warp-cross-language-benchmarks

Dać Haskell 4 rdzenie i może zrobić 100k (proste) żądania na sekundę w jednej aplikacji. Węzeł nie może wykonać tak wielu zadań i nie może skalować pojedynczej aplikacji między rdzeniami. I nie musisz nic robić, aby czerpać to, ponieważ Haskell runtime nie jest blokowanie. Jedynym innym (stosunkowo powszechnym) językiem, który ma wbudowane nieblokujące IO, jest Erlang.

 5
Author: Greg Weber,
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-06-23 02:20:46

IMHO eventy są dobre, ale programowanie za pomocą wywołań zwrotnych nie jest.

Większość problemów, które sprawiają, że kodowanie i debugowanie aplikacji internetowych jest wyjątkowe, wynika z tego, co czyni je skalowalnymi i elastycznymi. Najważniejszy, bezpaństwowy charakter HTTP. Zwiększa to nawigację, ale narzuca to inwersję sterowania, gdzie element IO (w tym przypadku serwer WWW) wywołuje różne procedury obsługi w kodzie aplikacji. Ten model zdarzenia - lub model callback, dokładniej powiedział- jest koszmarem, ponieważ wywołania zwrotne nie dzielą zakresów zmiennych, a intuicyjny widok nawigacji jest utracony. Bardzo trudno jest zapobiec wszystkim możliwym zmianom stanu, gdy użytkownik nawiguje między innymi w tę iz powrotem.

Można powiedzieć, że problemy są podobne do programowania GUI, gdzie model zdarzeń działa dobrze, ale GUI nie mają nawigacji ani przycisku Wstecz. To mnoży możliwe przejścia stanu w aplikacjach internetowych. Wynik próby rozwiązania problem ten to ciężkie ramy ze skomplikowanymi konfiguracjami mnóstwo wszechobecnych magicznych identyfikatorów bez kwestionowania źródła problemu: model wywołania zwrotnego i jego nieodłączny brak współdzielenia zmiennych zakresów i brak sekwencjonowania, więc sekwencja musi być skonstruowana przez łączenie identyfikatorów.

Istnieją sekwencyjne frameworki takie jak ocsigen (ocaml) seaside (smalltalk) WASH (Haskell) i mflow (Haskell), które rozwiązują problem zarządzania państwem podczas utrzymanie żeglowności i wypoczynku. w tych ramach programista może wyrazić nawigację jako imperatywną sekwencję, w której program wysyła strony i czeka na odpowiedzi w jednym wątku, zmienne są w zakresie, a przycisk Wstecz działa automatycznie. To z natury tworzy krótszy, bezpieczniejszy i bardziej czytelny kod, w którym nawigacja jest wyraźnie widoczna dla programisty. (fair warning: im the developer of mflow)

 5
Author: agocorona,
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-04-30 11:44:28
 1
Author: Chawathe Vipul,
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-02-01 14:35:30