Co to jest oprogramowanie pośredniczące w szafie w Ruby? Nie znalazłem dobrego wytłumaczenia tego, co rozumieją przez „oprogramowanie pośrednie”.
ruby-on-rails
ruby
http
web-applications
rack
chrisgoyal
źródło
źródło
Odpowiedzi:
Regał jako projekt
Oprogramowanie pośredniczące w szafie to coś więcej niż „sposób filtrowania żądania i odpowiedzi” - to implementacja wzorca projektowania potoków dla serwerów WWW korzystających z szafy .
Bardzo dokładnie oddziela poszczególne etapy przetwarzania żądania - oddzielenie problemów jest kluczowym celem wszystkich dobrze zaprojektowanych produktów oprogramowania.
Na przykład w szafie Rack mogę mieć oddzielne etapy rurociągu:
Uwierzytelnianie : czy po otrzymaniu żądania dane logowania użytkowników są prawidłowe? Jak zweryfikować to OAuth, podstawowe uwierzytelnianie HTTP, nazwę / hasło?
Autoryzacja : „czy użytkownik jest upoważniony do wykonania tego konkretnego zadania?”, Tj. Bezpieczeństwo oparte na rolach.
Buforowanie : czy przetworzyłem już to żądanie, czy mogę zwrócić wynik z pamięci podręcznej?
Dekoracja : jak mogę ulepszyć żądanie, aby ulepszyć przetwarzanie końcowe?
Monitorowanie wydajności i użytkowania : jakie statystyki mogę uzyskać z zapytania i odpowiedzi?
Wykonanie : faktycznie obsłużyć żądanie i podać odpowiedź.
Możliwość oddzielenia różnych etapów (i opcjonalnie ich uwzględnienia) jest wielką pomocą w tworzeniu dobrze zorganizowanych aplikacji.
Społeczność
Istnieje również świetny ekosystem rozwijający się wokół oprogramowania pośredniczącego w szafach - powinieneś być w stanie znaleźć gotowe komponenty do montażu w szafie, aby wykonać wszystkie powyższe kroki i więcej. Zobacz wiki GitHub Rack, aby uzyskać listę oprogramowania pośredniego .
Co to jest oprogramowanie pośrednie?
Oprogramowanie pośrednie to straszny termin, który odnosi się do dowolnego komponentu / biblioteki oprogramowania, który pomaga, ale nie jest bezpośrednio zaangażowany w wykonanie jakiegoś zadania. Bardzo częstymi przykładami są rejestrowanie, uwierzytelnianie i inne typowe komponenty przetwarzania poziomego . Są to rzeczy, których wszyscy potrzebują w wielu aplikacjach, ale niewiele osób jest zainteresowanych (lub powinno być) budowaniem siebie.
Więcej informacji
Komentarz na temat tego, że jest to sposób na filtrowanie żądań, prawdopodobnie pochodzi z odcinka RailsCast 151: Raster Middleware .
Oprogramowanie pośrednie Rack ewoluowało z Rack, a wprowadzenie do oprogramowania pośredniego Rack jest bardzo dobre .
Jest intro dla oprogramowania pośredniego Wikipedia tutaj .
źródło
Po pierwsze, Rack to dokładnie dwie rzeczy:
Rack - interfejs serwera WWW
Podstawy stojaka to prosta konwencja. Każdy serwer sieciowy zgodny ze stelażem zawsze wywoła metodę wywołania na podanym mu obiekcie i poda wynik tej metody. Rack określa dokładnie, jak powinna wyglądać ta metoda wywołania i co ma zwrócić. To jest stojak.
Wypróbujmy to prosto. Użyję WEBrick jako serwera sieciowego zgodnego ze stelażem, ale wystarczy jeden z nich. Stwórzmy prostą aplikację internetową, która zwraca ciąg JSON. W tym celu utworzymy plik o nazwie config.ru. Plik config.ru zostanie automatycznie wywołany przez polecenie backup gem szafy, które po prostu uruchomi zawartość pliku config.ru na serwerze WWW zgodnym z szafą. Dodajmy więc do pliku config.ru:
Jak określa konwencja, nasz serwer ma metodę o nazwie call, która akceptuje skrót środowiskowy i zwraca tablicę o formie [status, nagłówki, treść], która ma być obsługiwana przez serwer WWW. Wypróbujmy to, po prostu wywołując rackup. Domyślny serwer zgodny ze stelażem, być może WEBrick lub Mongrel uruchomi się i natychmiast zaczeka na żądania.
Przetestujmy nasz nowy serwer JSON poprzez zwijanie lub odwiedzanie adresu URL
http://localhost:9292/hello.json
i voila:To działa. Wspaniały! To podstawa każdego frameworka internetowego, czy to Railsów, czy Sinatry. W pewnym momencie implementują metodę wywołania, pracują przez cały kod frameworka, a na koniec zwracają odpowiedź w typowej formie [status, nagłówki, treść].
Na przykład w Ruby on Rails żądania stelaża trafiają do
ActionDispatch::Routing.Mapper
klasy, która wygląda następująco:Więc w zasadzie Railsy sprawdzają, zależnie od skrótu env, jeśli jakaś trasa jest zgodna. Jeśli tak, przekazuje skrót env do aplikacji w celu obliczenia odpowiedzi, w przeciwnym razie natychmiast odpowiada 404. Tak więc każdy serwer sieciowy, który jest zgodny z konwencją interfejsu stelażowego, może obsłużyć w pełni wydaną aplikację Railsową.
Middleware
Rack obsługuje również tworzenie warstw oprogramowania pośredniego. Zasadniczo przechwytują zapytanie, coś z nim robią i przekazują dalej. Jest to bardzo przydatne do wszechstronnych zadań.
Powiedzmy, że chcemy dodać rejestrowanie do naszego serwera JSON, który mierzy również czas trwania żądania. Możemy po prostu utworzyć rejestrator oprogramowania pośredniego, który robi dokładnie to:
Po utworzeniu zapisuje sobie kopię faktycznej aplikacji do montażu w szafie. W naszym przypadku jest to przykład naszego serwera JSONServer. Rack automatycznie wywołuje metodę wywołania w oprogramowaniu pośrednim i oczekuje z powrotem
[status, headers, body]
tablicy, tak jak zwraca nasz JSONServer.Tak więc w tym oprogramowaniu pośrednim jest brany punkt początkowy, następnie wykonuje się rzeczywiste wywołanie JSONServer
@app.call(env)
, a następnie program rejestrujący wysyła wpis rejestrowania i ostatecznie zwraca odpowiedź jako[@status, @headers, @body]
.Aby nasz mały rackup.ru używał tego oprogramowania pośredniego, dodaj do niego RackLogger w następujący sposób:
Zrestartuj serwer i voila, wypisuje log na każde żądanie. Rack pozwala dodawać wiele programów pośrednich, które są wywoływane w kolejności ich dodawania. To po prostu świetny sposób na dodanie funkcjonalności bez zmiany rdzenia aplikacji w szafie.
Rack - klejnot
Chociaż stojak - przede wszystkim - jest konwencją, jest również klejnotem, który zapewnia doskonałą funkcjonalność. Jeden z nich, którego już używaliśmy dla naszego serwera JSON, polecenie rackup. Ale jest więcej! Klejnot do szafy zapewnia niewiele aplikacji do wielu zastosowań, takich jak serwowanie plików statycznych lub nawet całych katalogów. Zobaczmy, jak udostępniamy prosty plik, na przykład bardzo prosty plik HTML znajdujący się w htmls / index.html:
Być może chcemy udostępnić ten plik z katalogu głównego witryny, dlatego dodajmy do naszego pliku config.ru:
Jeśli odwiedzimy
http://localhost:9292
, zobaczymy, że nasz plik HTML jest doskonale renderowany. To było łatwe, prawda?Dodajmy cały katalog plików javascript, tworząc niektóre pliki javascript w / javascripts i dodając następujące elementy do config.ru:
Uruchom ponownie serwer i odwiedź,
http://localhost:9292/javascript
a zobaczysz listę wszystkich plików javascript, które możesz teraz dołączyć bezpośrednio z dowolnego miejsca.źródło
Przez dłuższy czas miałem problem ze zrozumieniem samego Racka. Zrozumiałem to dopiero po samodzielnym stworzeniu tego miniaturowego serwera Ruby . Na blogu podzieliłem się swoją wiedzą na temat Rack (w formie opowiadania): http://gauravchande.com/what-is-rack-in-ruby-rails
Informacje zwrotne są mile widziane.
źródło
config.ru
minimalny możliwy do uruchomienia przykładUruchom
rackup
i odwiedźlocalhost:9292
. Dane wyjściowe to:Jest więc jasne, że
Middleware
otacza i wywołuje główną aplikację. Dlatego jest w stanie wstępnie przetworzyć żądanie i przetworzyć odpowiedź w dowolny sposób.Jak wyjaśniono na stronie : http://guides.rubyonrails.org/rails_on_rack.html#action-dispatcher-middleware-stack , Rails korzysta z oprogramowania pośredniego Rack dla wielu swoich funkcji, a także możesz dodać swoje własne za pomocą
config.middleware.use
metod rodzinnych.Zaletą implementacji funkcjonalności w oprogramowaniu pośrednim jest to, że można go ponownie użyć w dowolnym środowisku Rack, a więc we wszystkich głównych Ruby, a nie tylko w Railsach.
źródło
Oprogramowanie pośredniczące w szafie jest sposobem na odfiltrowanie żądania i odpowiedzi przychodzących do aplikacji. Komponent oprogramowania pośredniego znajduje się między klientem a serwerem, przetwarzając żądania przychodzące i odpowiedzi wychodzące, ale to coś więcej niż interfejs, za pomocą którego można rozmawiać z serwerem WWW. Służy do grupowania i porządkowania modułów, które zwykle są klasami Ruby, i określania zależności między nimi. Moduł oprogramowania pośredniczącego w szafie musi tylko: - mieć konstruktora, który przyjmuje następną aplikację na stosie jako parametr - reagować na metodę „wywołania”, która jako parametr przyjmuje skrót środowiska. Zwracana wartość z tego wywołania to tablica: kodu statusu, skrótu środowiska i treści odpowiedzi.
źródło
Użyłem oprogramowania pośredniego Rack, aby rozwiązać kilka problemów:
Dało to dość eleganckie poprawki w obu przypadkach.
źródło
Co to jest Rack?
Rack zapewnia minimalny interfejs pomiędzy serwerami obsługującymi Ruby i frameworki Ruby.
Za pomocą Rack możesz napisać aplikację Rack.
Rack przekaże skrót środowiska (skrót, zawarty w żądaniu HTTP klienta, składającym się z nagłówków podobnych do CGI) do aplikacji w stojaku, która może korzystać z rzeczy zawartych w tym skrócie, aby robić, co chce.
Co to jest aplikacja do montażu w szafie serwerowej?
Aby użyć Rack, musisz dostarczyć „aplikację” - obiekt, który reaguje na
#call
metodę za pomocą funkcji skrótu środowiska jako parametru (zazwyczaj zdefiniowanej jakoenv
).#call
musi zwrócić tablicę dokładnie trzech wartości:each
).Możesz napisać aplikację Rack, która zwróci taką tablicę - zostanie ona odesłana do klienta przez Rack, w odpowiedzi (faktycznie będzie to instancja klasy
Rack::Response
[kliknij, aby przejść do dokumentów]).Bardzo prosta aplikacja do montażu w szafie:
gem install rack
config.ru
plik - Rack wie, że tego szuka.Będziemy tworzyć niewielką aplikację regałowe, które zwraca odpowiedź (instancję
Rack::Response
) Kto ciała Response jest tablicą, która zawiera ciąg:"Hello, World!"
.Uruchomimy lokalny serwer za pomocą polecenia
rackup
.Odwiedzając odpowiedni port w naszej przeglądarce, zobaczymy „Witaj, świecie!” renderowane w rzutni.
Uruchom serwer lokalny
rackup
i odwiedź localhost: 9292 , powinieneś zobaczyć „Witaj, świecie!” renderowane.Nie jest to wyczerpujące wyjaśnienie, ale zasadniczo to, co się tutaj dzieje, polega na tym, że klient (przeglądarka) wysyła żądanie Rack do Rack, za pośrednictwem lokalnego serwera, a Rack tworzy instancję
MessageApp
i uruchamia sięcall
, przekazując funkcję Hash środowiska jako parametr do metody (env
argument).Rack pobiera wartość zwracaną (tablicę) i używa jej do utworzenia instancji
Rack::Response
i przesyła ją z powrotem do klienta. Przeglądarka używa magii do drukowania „Witaj, świecie!” do ekranu.Nawiasem mówiąc, jeśli chcesz zobaczyć, jak wygląda skrót środowiska, po prostu umieść go
puts env
pod spodemdef call(env)
.Choć jest minimalna, napisałeś tutaj o aplikacji Rack!
Interakcja aplikacji Rack z hashem środowiska przychodzącego
W naszej małej aplikacji Rack możemy wchodzić w interakcje z
env
skrótem (zobacz tutaj więcej na temat skrótu środowiska).Zaimplementujemy możliwość wprowadzania przez użytkownika własnego ciągu zapytania do adresu URL, dlatego ciąg ten będzie obecny w żądaniu HTTP, enkapsulowany jako wartość w jednej z par klucz / wartość skrótu środowiska.
Nasza aplikacja Rack uzyska dostęp do ciągu zapytania z mieszania środowiska i odeśle go z powrotem do klienta (w tym przypadku naszej przeglądarki) za pośrednictwem treści w odpowiedzi.
Z dokumentacji Rack na temat skrótu środowiska: „QUERY_STRING: Część adresu URL żądania, która następuje po znaku?, Jeśli istnieje. Może być pusta, ale zawsze wymagana!”
Teraz
rackup
i odwiedźlocalhost:9292?hello
(?hello
jest ciąg zapytania) i powinieneś zobaczyć „witaj” renderowane w okienku ekranu.Rack Middleware
Będziemy:
MessageSetter
,env
,MessageSetter
wstawi'MESSAGE'
klucz do skrótu env, jego wartością jest'Hello, World!'
if , jeślienv['QUERY_STRING']
jest pusty;env['QUERY_STRING']
Jeśli nie,@app.call(env)
-@app
będąc obok aplikacji w „stack”:MessageApp
.Po pierwsze, wersja „długiej ręki”:
Z dokumentacji Rack :: Builder widzimy, że
Rack::Builder
implementuje małą DSL do iteracyjnego konstruowania aplikacji Rack. Zasadniczo oznacza to, że możesz zbudować „stos” składający się z co najmniej jednego oprogramowania pośredniego i aplikacji „najniższego poziomu” do wysłania. Wszystkie żądania przechodzące do aplikacji na najniższym poziomie zostaną najpierw przetworzone przez oprogramowanie pośrednie.#use
określa oprogramowanie pośrednie, które ma być używane na stosie. Jako argument przyjmuje oprogramowanie pośrednie.Oprogramowanie pośredniczące w szafie musi:
call
metodę, która przyjmuje jako parametr parametr skrótu środowiska.W naszym przypadku „Middleware” to
MessageSetter
„konstruktor” toinitialize
metoda MessageSetter , „następna aplikacja” na stosieMessageApp
.Więc tutaj, ze względu na to, co
Rack::Builder
robi pod maskąapp
argumentMessageSetter
„sinitialize
metody jestMessageApp
.(obejrzyj się wyżej, zanim przejdziesz dalej)
Dlatego każdy element oprogramowania pośredniego zasadniczo „przekazuje” istniejący skrót środowiska do następnej aplikacji w łańcuchu - więc masz możliwość mutowania tego skrótu środowiska w oprogramowaniu pośrednim przed przekazaniem go do następnej aplikacji na stosie.
#run
pobiera argument, który jest obiektem, który odpowiada#call
i zwraca odpowiedź Rack (instancjaRack::Response
).Wnioski
Korzystając z niego
Rack::Builder
, możesz konstruować łańcuchy oprogramowania pośredniego, a każde żądanie aplikacji zostanie przetworzone przez każde oprogramowanie pośrednie, zanim ostatecznie zostanie przetworzone przez ostatni element stosu (w naszym przypadkuMessageApp
). Jest to niezwykle przydatne, ponieważ oddziela różne etapy przetwarzania żądań. Jeśli chodzi o „rozdzielenie obaw”, nie może być dużo czystsze!Możesz zbudować „potok zapytań” składający się z kilku Middlewares, które zajmują się takimi rzeczami jak:
(powyżej punktorów z innej odpowiedzi w tym wątku)
Często zobaczysz to w profesjonalnych aplikacjach Sinatra. Sinatra używa Rack! Zobacz tutaj do zdefiniowania co Sinatra JEST !
Na koniec
config.ru
możemy napisać w skrócie, oferując dokładnie taką samą funkcjonalność (i to zwykle zobaczysz):Aby dokładniej pokazać, co
MessageApp
się dzieje, oto jego wersja „długiej ręki”, która wyraźnie pokazuje, że#call
tworzy nową instancjęRack::Response
, z wymaganymi trzema argumentami.Przydatne linki
źródło
Rack - Interfejs b / w Web & App Server
Rack to pakiet Ruby, który zapewnia interfejs serwera WWW do komunikacji z aplikacją. Łatwo jest dodać składniki oprogramowania pośredniego między serwerem WWW a aplikacją, aby zmodyfikować sposób działania żądania / odpowiedzi. Komponent oprogramowania pośredniego znajduje się między klientem a serwerem, przetwarzając żądania przychodzące i odpowiedzi wychodzące.
Krótko mówiąc, jest to po prostu zestaw wskazówek, jak serwer i aplikacja Rails (lub jakakolwiek inna aplikacja internetowa Ruby) powinny ze sobą rozmawiać .
Aby użyć Rack, podaj „aplikację”: obiekt, który reaguje na metodę wywołania, przyjmując skrót środowiska jako parametr i zwracając tablicę z trzema elementami:
Aby uzyskać więcej wyjaśnień, możesz skorzystać z poniższych łączy.
W szynach mamy config.ru jako plik szafy, możesz uruchomić dowolny plik szafy za pomocą
rackup
polecenia. Domyślny port to9292
. Aby to przetestować, wystarczy uruchomićrackup
w katalogu Rails i zobaczyć wynik. Możesz także przypisać port, na którym chcesz go uruchomić. Polecenie uruchomienia pliku szafy na dowolnym określonym porcie toźródło
Rack to klejnot, który zapewnia prosty interfejs do abstrakcyjnego żądania / odpowiedzi HTTP. Rack znajduje się między szkieletami sieci (Rails, Sinatra itp.) A serwerami WWW (jednorożec, puma) jako adapter. Z powyższego obrazu utrzymuje to całkowicie niezależność serwera jednorożca od wiedzy o szynach, a szyny nie wiedzą o jednorożcu. To dobry przykład luźnego sprzężenia , oddzielenia problemów .
Powyższe zdjęcie pochodzi z tej konferencji na temat szyn na stojaku https://youtu.be/3PnUV9QzB0g. Polecam obejrzeć to dla głębszego zrozumienia.
źródło