Jak programowanie sieciowe reprezentowane jest w Ruby?
W tym artykule przyjrzymy się następującym tematom:
- biblioteka
socket
- biblioteka
Net
Wprowadzenie
Z biegiem czasu, komunikacja przez komputery była niezbędna dla ewolucji informatyki na świecie. W rzeczy samej, pozwoliła nam na:
- wymianę informacji (czat, poczta itp.)
- współdzielenie plików (FTP itp.)
- rozpowszechnianie idei, opinii, przekazów (Internet, ...)
- tworzenie nowych możliwości biznesowych
W tym artykule zobaczymy, jak Ruby zaimplementował programowanie sieciowe w swojej bibliotece standardowej.
Biblioteka socket
Po pierwsze, jeśli nie wiesz, co to jest gniazdo (socket):
Gniazda są punktami końcowymi dwukierunkowego kanału komunikacyjnego. Mogą komunikować się w ramach procesu, pomiędzy procesami na tej samej maszynie lub pomiędzy różnymi maszynami.
Biblioteka socket
jest odpowiedzialna za zapewnienie dostępu do różnego rodzaju istniejących gniazd:
- Gniazdo TCP - poprzez klasę
TCPSocket
- Gniazdo UDP - poprzez klasę
UDPSocket
- Gniazdo UNIX - poprzez klasę
UnixSocket
- itp.
Biblioteka ta jest częścią biblioteki standardowej Ruby. W Rubym, root class każdego Socket
jest klasa BasicSocket
.
require 'socket'
BasicSocket.superclass # => IO
BasicSocket.methods(false) # => [:for_fd, :do_not_reverse_lookup, :do_not_reverse_lookup=]
BasicSocket.instance_methods(false) # => [:setsockopt, :connect_address, :local_address, :close_read, :sendmsg, :close_write, :remote_address, :recv_nonblock, :sendmsg_nonblock, :recvmsg, :recvmsg_nonblock, :do_not_reverse_lookup, :do_not_reverse_lookup=, :shutdown, :getsockopt, :getsockname, :getpeername, :getpeereid, :recv, :send]
Ta klasa dziedziczy po IO
. Klasa IO
jest odpowiedzialna za obsługę strumienia wejściowego (I nput) i wyjściowego (O utput) - takich jak instancje File
, $stdin
, $stdout
lub $stderr
. Oznacza to, że nasz socket
jest interpretowany jako strumień I/O.
Ponadto klasa BasicSocket
oferuje kilka metod dostępu do właściwości socket
i kilka metod zapisu i odczytu z gniazda - takich jak blokujące i nieblokujące read
i write
. Klasy TCPSocket
, UDPSocket
i UNIXSocket
wywodzą się z BasicSocket
.
Właściwie TCPSocket i UDPSocket wywodzą się z IPSocket, który wywodzi się z BasicSocket
. Wszystkie one używają procedur zdefiniowanych w BasicSocket
i implementują protokół związany z ich typem gniazda:
- protokół
TCP
dlaTCPSocket
- protokół
UDP
dlaUDPSocket
- mechanizm
IPC
dlaUNIXSocket
Biblioteka socket
jest odpowiedzialna za obsługę komunikacji niskopoziomowej poprzez protokół internetowy (UDP i TCP) oraz międzyprocesowy mechanizm komunikacji.
Teraz zobaczmy, jak Ruby implementuje wysokopoziomowe protokoły, takie jak HTTP
, IMAP
, SMTP
i FTP
.
Biblioteka Net
Biblioteka Net
jest odpowiedzialna za zapewnienie implementacji protokołów wysokiego poziomu. Obsługiwane protokoły to FTP
, HTTP
, IMAP
, POP
i SMTP
.
Widzimy, że wszystkie te protokoły są zaimplementowane w określonej klasie w przestrzeni nazw Net
. Również te klasy wywodzą się z klasy Net::Protocol
.
Przyjrzyjmy się zawartości tej klasy.
require 'net/protocol'
Net::Protocol.superclass # => Object
Net::Protocol.methods(false) # => [:protocol_param]
Net::Protocol.instance_methods(false) # => []
Klasa Net::Protocol
dziedziczy po Object
- klasie domyślnie dziedziczonej w Ruby.
Zapraszam do przeczytania mojego artykułu na temat Ruby Object Model jeśli nie znasz klasy Object
w Ruby.
Implementuje również metodę klasową protocol_param
, która jest wykorzystywana do definiowania oczekiwany parametrów protokołu. Jest to bardzo lekki obiekt. Poza tym, wczytanie biblioteki net/protocol
dodaje trochę więcej niż samą klasę.
Jeśli nie znasz metody Kernel#require
w Ruby, możesz przeczytać o używaniu require do wczytywania pliku lub biblioteki w Ruby.
Rzeczywiście, oprócz klasy Net::Protocol
, biblioteka net/protocol
:
- dodaje zestaw klas błędów.
- wczytuje inne biblioteki potrzebne przez protokoły - takie jak biblioteka
socket
. - dodaje zestaw klas do kontroli operacji read/write poprzez gniazda -
BufferedIO
,WriteAdapter
, itp.
Tak więc, klasa, która wywodzi się z Net::Protocol
zapewnia implementację danego protokołu i obsługuje błędy oraz operacje na strumieniu I/O przy użyciu narzędzi dostarczanych przez bibliotekę net/protocol
.
Wniosek
Ponieważ Ruby jest w pełni obiektowym językiem programowania, implementacja programowania sieciowego wykorzystuje wszystkie narzędzia dostarczane przez te języki - takie jak namespacing, dziedziczenie, klasa root, obsługa błędów, wczytywanie zależności (słowo kluczowe require
).
Ruby implementuje również niskopoziomowe i wysokopoziomowe protokoły sieciowe w dwóch różnych bibliotekach: socket
i net/*
.
I co najważniejsze, korzystając z abstrakcji dostarczonej przez Ruby można łatwo wdrożyć nowy protokół - poprzez dziedziczenie BasicSocket
lub Net::Protocol
w zależności od Twoich potrzeb.
Oryginał tekstu w języku angielskim przeczytasz tutaj.