Omówienie projektu Katana
Autor : Howard Dierking
Platforma ASP.NET jest już od ponad dziesięciu lat, a platforma umożliwiła opracowywanie niezliczonych witryn internetowych i usług. W miarę rozwoju strategii tworzenia aplikacji internetowych struktura była w stanie rozwijać się w krokach za pomocą technologii takich jak ASP.NET MVC i ASP.NET internetowy interfejs API. W miarę jak opracowywanie aplikacji internetowych zajmuje kolejny ewolucyjny krok w świecie przetwarzania w chmurze, projekt Katana udostępnia podstawowy zestaw składników do ASP.NET aplikacji, umożliwiając im elastyczne, przenośne, lekkie i zapewniające lepszą wydajność — mówiąc inaczej, projekt Katana optymalizuje aplikacje ASP.NET.
Dlaczego Katana – Dlaczego teraz?
Niezależnie od tego, czy omawia się strukturę deweloperów, czy produkt użytkownika końcowego, ważne jest, aby zrozumieć podstawowe motywacje do tworzenia produktu — a część z nich zawiera informacje o tym, do kogo został utworzony produkt. ASP.NET został pierwotnie utworzony z myślą o dwóch klientach.
Pierwsza grupa klientów była klasycznymi deweloperami platformy ASP. W tym czasie platforma ASP była jedną z podstawowych technologii tworzenia dynamicznych, opartych na danych witryn internetowych i aplikacji przez przeplatanie znaczników i skryptu po stronie serwera. Środowisko uruchomieniowe ASP dostarczyło skrypt po stronie serwera z zestawem obiektów, które abstrakcje podstawowych aspektów podstawowego protokołu HTTP i serwera sieci Web oraz zapewniały dostęp do dodatkowych usług, takich jak zarządzanie sesjami i stanami aplikacji, pamięć podręczna itp. Chociaż zaawansowane, klasyczne aplikacje ASP stały się wyzwaniem dla zarządzania w miarę wzrostu rozmiaru i złożoności. Było to w dużej mierze spowodowane brakiem struktury w środowiskach skryptowych w połączeniu z duplikowaniem kodu wynikającego z przeplatania kodu i znaczników. Aby wykorzystać zalety klasycznej platformy ASP podczas rozwiązywania niektórych problemów, ASP.NET skorzystała z organizacji kodu dostarczanej przez języki obiektowe .NET Framework przy jednoczesnym zachowaniu modelu programowania po stronie serwera, do którego przyzwyczaili się klasyczni deweloperzy asp.
Druga grupa klientów docelowych dla ASP.NET to deweloperzy aplikacji biznesowych systemu Windows. W przeciwieństwie do klasycznych deweloperów asp, którzy byli przyzwyczajeni do pisania znaczników HTML i kodu w celu wygenerowania większej liczby znaczników HTML, deweloperzy WinForms (tacy jak deweloperzy VB6 przed nimi) byli przyzwyczajeni do środowiska czasu projektowania, które obejmowały kanwę i bogaty zestaw kontrolek interfejsu użytkownika. Pierwsza wersja ASP.NET — znana również jako "Web Forms" zapewnia podobne środowisko czasu projektowania wraz z modelem zdarzeń po stronie serwera dla składników interfejsu użytkownika i zestawem funkcji infrastruktury (takich jak ViewState) w celu utworzenia bezproblemowego środowiska dewelopera między programowaniem po stronie klienta i serwera. Web Forms skutecznie ukrywać bezstanową naturę sieci Web w ramach stanowego modelu zdarzeń, który był znany deweloperom winForms.
Wyzwania podniesione przez model historyczny
Wynik netto był dojrzałym, rozbudowanym w funkcje środowiskiem uruchomieniowym i modelem programowania dla deweloperów. Jednak z tym bogactwem cech przyszedł kilka godnych uwagi wyzwań. Po pierwsze, struktura była monolityczna, a logicznie różne jednostki funkcjonalności są ściśle powiązane w tym samym zestawie System.Web.dll (na przykład podstawowe obiekty HTTP ze strukturą formularzy sieci Web). Po drugie, ASP.NET została uwzględniona w ramach większej .NET Framework, co oznaczało, że czas między wydaniami wynosił kolejność lat. Utrudniło to ASP.NET nadążanie za wszystkimi zmianami, które wystąpiły w szybkim rozwoju aplikacji internetowych. Na koniec, System.Web.dll się w połączeniu z kilkoma różnymi sposobami określonej opcji hostingu sieci Web: Internet Information Services (IIS).
Kroki ewolucyjne: ASP.NET MVC i internetowy interfejs API ASP.NET
A wiele zmian miało miejsce w tworzeniu aplikacji internetowych! Aplikacje internetowe były coraz częściej opracowywane jako seria małych, skoncentrowanych składników, a nie dużych struktur. Liczba składników, a także częstotliwość ich wydawania zwiększała się w coraz szybszym tempie. Było jasne, że utrzymanie tempa pracy z siecią Web wymagałoby, aby struktury były mniejsze, oddzielone i bardziej skoncentrowane, a nie większe i bardziej bogate w funkcje, dlatego zespół ASP.NET podjął kilka kroków ewolucyjnych, aby umożliwić ASP.NET jako rodzina podłączonych składników sieci Web, a nie jednej struktury.
Jedną z wczesnych zmian był wzrost popularności dobrze znanego wzorca projektowego mvC (model-view-controller) dzięki platformom deweloperów internetowych, takich jak Ruby on Rails. Ten styl tworzenia aplikacji internetowych dał deweloperowi większą kontrolę nad adiustacjami aplikacji, zachowując jednocześnie separację znaczników i logiki biznesowej, która była jednym z początkowych punktów sprzedaży dla ASP.NET. Aby sprostać zapotrzebowaniu na ten styl tworzenia aplikacji internetowych, firma Microsoft skorzystała z okazji, aby lepiej ustawić się na przyszłość, opracowując ASP.NET MVC poza pasmem (i nie dołączając jej do .NET Framework). ASP.NET MVC został wydany jako niezależny plik do pobrania. Dało to zespołowi inżynieryjnemu elastyczność dostarczania aktualizacji znacznie częściej niż wcześniej.
Kolejną ważną zmianą w tworzeniu aplikacji internetowych było przejście od dynamicznych, generowanych przez serwer stron internetowych do statycznego początkowego narzutu z dynamicznymi sekcjami strony wygenerowanej na podstawie skryptu po stronie klienta komunikującego się z internetowymi interfejsami API zaplecza za pośrednictwem żądań AJAX. Ta zmiana architektury przyczyniła się do wzrostu internetowych interfejsów API i rozwoju platformy ASP.NET Web API. Podobnie jak w przypadku ASP.NET MVC, wydanie internetowego interfejsu API ASP.NET stanowi kolejną okazję do rozwoju ASP.NET jako bardziej modułowej struktury. Zespół inżynierów skorzystał z możliwości i zbudował ASP.NET internetowy interfejs API, tak aby nie miał zależności od żadnego z podstawowych typów struktur znalezionych w System.Web.dll. Umożliwiło to dwie rzeczy: po pierwsze, oznaczało to, że ASP.NET internetowy interfejs API może ewoluować w całkowicie samodzielny sposób (i może kontynuować iterowanie szybko, ponieważ jest dostarczany za pośrednictwem narzędzia NuGet). Po drugie, ponieważ nie było żadnych zależności zewnętrznych do System.Web.dll, a zatem nie ma zależności od usług IIS, ASP.NET internetowy interfejs API obejmował możliwość uruchamiania na hoście niestandardowym (na przykład aplikacji konsolowej, usługi systemu Windows itp.)
Przyszłość: zwinne ramy
Dzięki oddzieleniu składników struktury od siebie, a następnie udostępnieniu ich w programie NuGet, struktury mogą teraz iterować niezależnie i szybciej. Ponadto możliwości i elastyczność możliwości samoobsługowego hostowania interfejsu API sieci Web okazały się bardzo atrakcyjne dla deweloperów, którzy chcieli małego, lekkiego hosta dla swoich usług. Okazało się tak atrakcyjne, w rzeczywistości, że inne struktury również chciały tej możliwości, a to pojawiło się nowe wyzwanie w tym, że każda struktura działała we własnym procesie hosta na własnym adresie bazowym i musiała być zarządzana (uruchomiona, zatrzymana itp.) niezależnie. Nowoczesna aplikacja internetowa zazwyczaj obsługuje statyczną obsługę plików, dynamiczne generowanie stron, internetowy interfejs API i ostatnio powiadomienia w czasie rzeczywistym/wypychane. Oczekiwanie, że każda z tych usług powinna być uruchamiana i zarządzana niezależnie, po prostu nie była realistyczna.
Potrzebna była pojedyncza abstrakcja hostingu, która umożliwi deweloperowi tworzenie aplikacji z różnych składników i struktur, a następnie uruchamianie tej aplikacji na hoście pomocniczym.
Otwarty interfejs internetowy dla platformy .NET (OWIN)
Zainspirowany korzyściami uzyskanymi przez aplikację Rack w społeczności języka Ruby, kilku członków społeczności platformy .NET postanowiło utworzyć abstrakcję między serwerami internetowymi i składnikami struktury. Dwa cele projektowe dla abstrakcji OWIN były proste i że zajęło najmniej możliwych zależności w innych typach struktur. Te dwa cele pomagają zapewnić:
- Nowe składniki można łatwiej opracowywać i wykorzystywać.
- Aplikacje mogą być łatwiej przenosine między hostami i potencjalnie całymi platformami/systemami operacyjnymi.
Wynikowa abstrakcja składa się z dwóch podstawowych elementów. Pierwszy to słownik środowiskowy. Ta struktura danych jest odpowiedzialna za przechowywanie wszystkich stanów niezbędnych do przetwarzania żądania HTTP i odpowiedzi, a także dowolnego odpowiedniego stanu serwera. Słownik środowiskowy jest zdefiniowany w następujący sposób:
IDictionary<string, object>
Serwer sieci Web zgodny z OWIN jest odpowiedzialny za wypełnianie słownika środowiska danymi, takimi jak strumienie treści i kolekcje nagłówków dla żądania HTTP i odpowiedzi. Następnie obowiązkiem składników aplikacji lub platformy jest wypełnienie lub zaktualizowanie słownika dodatkowymi wartościami i zapisanie ich w strumieniu treści odpowiedzi.
Oprócz określania typu słownika środowiskowego specyfikacja OWIN definiuje listę podstawowych par wartości klucza słownika. Na przykład w poniższej tabeli przedstawiono wymagane klucze słownika dla żądania HTTP:
Nazwa klucza | Opis wartości |
---|---|
"owin.RequestBody" |
Strumień z treścią żądania, jeśli istnieje. Element Stream.Null MOŻE być używany jako symbol zastępczy, jeśli nie ma treści żądania. Zobacz Treść żądania. |
"owin.RequestHeaders" |
Nagłówek IDictionary<string, string[]> żądania. Zobacz Nagłówki. |
"owin.RequestMethod" |
Element string zawierający metodę żądania HTTP żądania (np. "GET" , "POST" ). |
"owin.RequestPath" |
Element string zawierający ścieżkę żądania. Ścieżka MUSI być względna względem "głównego" delegata aplikacji; zobacz Ścieżki. |
"owin.RequestPathBase" |
Element string zawierający część ścieżki żądania odpowiadającą "głównemu" delegatowi aplikacji. Zobacz Ścieżki. |
"owin.RequestProtocol" |
Element string zawierający nazwę i wersję protokołu (np. "HTTP/1.0" lub "HTTP/1.1" ). |
"owin.RequestQueryString" |
Element string zawierający składnik ciągu zapytania identyfikatora URI żądania HTTP bez wiodącego ciągu "?" (np. "foo=bar&baz=quux" ). Wartość może być pustym ciągiem. |
"owin.RequestScheme" |
Element string zawierający schemat identyfikatora URI używany dla żądania (np. "http" , "https" ), zobacz Schemat identyfikatora URI. |
Drugim kluczowym elementem OWIN jest delegat aplikacji. Jest to sygnatura funkcji, która służy jako podstawowy interfejs między wszystkimi składnikami w aplikacji OWIN. Definicja delegata aplikacji jest następująca:
Func<IDictionary<string, object>, Task>;
Następnie delegat aplikacji jest po prostu implementacją typu delegata Func, w którym funkcja akceptuje słownik środowiska jako dane wejściowe i zwraca zadanie. Ten projekt ma kilka konsekwencji dla deweloperów:
- Istnieje bardzo mała liczba zależności typu wymaganych do zapisu składników OWIN. Znacznie zwiększa to dostępność OWIN deweloperom.
- Projekt asynchroniczny umożliwia efektywne działanie abstrakcji dzięki obsłudze zasobów obliczeniowych, szczególnie w przypadku operacji intensywnie korzystających z operacji we/wy.
- Ponieważ delegat aplikacji jest niepodzielnej jednostki wykonywania, a słownik środowiska jest przenoszony jako parametr na delegata, składniki OWIN można łatwo połączyć w łańcuch w celu utworzenia złożonych potoków przetwarzania HTTP.
Z perspektywy implementacji OWIN jest specyfikacją (http://owin.org/html/owin.html). Jego celem nie jest następna struktura sieci Web, ale raczej specyfikacja sposobu interakcji struktur internetowych i serwerów sieci Web.
Jeśli zbadano elementy OWIN lub Katana, być może zauważysz również pakiet NuGet Owin i Owin.dll. Ta biblioteka zawiera pojedynczy interfejs [IAppBuilder]/dotnet/api/microsoft.aspnetcore.builder.iapplicationbuilder), który formalizuje i kodfikuje sekwencję uruchamiania opisaną w sekcji 4 specyfikacji OWIN. Chociaż nie jest to wymagane do kompilowania serwerów OWIN, interfejs [IAppBuilder]/dotnet/api/microsoft.aspnetcore.builder.iapplicationbuilder) zapewnia konkretny punkt odniesienia i jest używany przez składniki projektu Katana.
Projekt Katana
Podczas gdy zarówno specyfikacja OWIN, jak iOwin.dll są własnością społeczności i są prowadzone przez społeczność open source wysiłków, projekt Katana reprezentuje zestaw składników OWIN, które mimo open source są kompilowane i wydawane przez firmę Microsoft. Składniki te obejmują zarówno składniki infrastruktury, takie jak hosty i serwery, jak i składniki funkcjonalne, takie jak składniki uwierzytelniania i powiązania z platformami, takimi jak SignalR i ASP.NET internetowy interfejs API. Projekt ma następujące trzy cele wysokiego poziomu:
- Portable — składniki powinny być łatwo zastępowane nowymi składnikami, gdy staną się dostępne. Obejmuje to wszystkie typy składników, od platformy do serwera i hosta. Implikacją tego celu jest to, że struktury innych firm mogą bezproblemowo działać na serwerach firmy Microsoft, podczas gdy struktury firmy Microsoft mogą być potencjalnie uruchamiane na serwerach i hostach innych firm.
- Modularne/elastyczne — w przeciwieństwie do wielu struktur, które obejmują mnóstwo funkcji, które są domyślnie włączone, składniki projektu Katana powinny być małe i skoncentrowane, dając kontrolę deweloperowi aplikacji w określaniu, które składniki mają być używane w jej aplikacji.
- Uproszczone/wydajne/skalowalne — przez podzielenie tradycyjnego pojęcia struktury na zestaw małych, ukierunkowanych składników, które są dodawane jawnie przez dewelopera aplikacji, wynikowa aplikacja Katana może zużywać mniej zasobów obliczeniowych, a w rezultacie obsługiwać większe obciążenie niż w przypadku innych typów serwerów i struktur. Ponieważ wymagania aplikacji wymagają większej liczby funkcji z podstawowej infrastruktury, można je dodać do potoku OWIN, ale powinno to być jawną decyzją ze strony dewelopera aplikacji. Ponadto podstawianie składników niższego poziomu oznacza, że w miarę ich dostępności nowe serwery o wysokiej wydajności można bezproblemowo wprowadzać w celu poprawy wydajności aplikacji OWIN bez przerywania tych aplikacji.
Wprowadzenie ze składnikami Katana
Po raz pierwszy został wprowadzony, jednym z aspektów struktury Node.js , która natychmiast zwróciła uwagę ludzi, była prostota, z którą można utworzyć i uruchomić serwer sieci Web. Jeśli cele Katany zostały określone w świetle Node.js, można je podsumować, mówiąc, że Katana przynosi wiele korzyści zNode.js (i takich struktur) bez zmuszania dewelopera do wyrzucenia wszystkiego, co wie o tworzeniu ASP.NET aplikacji internetowych. Aby to stwierdzenie było prawdziwe, rozpoczęcie pracy z projektem Katana powinno być równie proste, aby Node.js.
Tworzenie "Hello world!"
Jedną z istotnych różnic między programowaniem w języku JavaScript a platformą .NET jest obecność (lub brak) kompilatora. W związku z tym punktem wyjścia dla prostego serwera Katana jest projekt programu Visual Studio. Jednak możemy zacząć od najbardziej minimalnych typów projektów: Puste ASP.NET aplikacji internetowej.
Następnie zainstalujemy pakiet NuGet Microsoft.Owin.Host.SystemWeb w projekcie. Ten pakiet zawiera serwer OWIN, który działa w potoku żądania ASP.NET. Można ją znaleźć w galerii NuGet i można ją zainstalować za pomocą okna dialogowego menedżera pakietów programu Visual Studio lub konsoli menedżera pakietów za pomocą następującego polecenia:
install-package Microsoft.Owin.Host.SystemWeb
Zainstalowanie Microsoft.Owin.Host.SystemWeb
pakietu spowoduje zainstalowanie kilku dodatkowych pakietów jako zależności. Jedną z tych zależności jest Microsoft.Owin
biblioteka , która udostępnia kilka typów pomocników i metod tworzenia aplikacji OWIN. Możemy użyć tych typów, aby szybko napisać następujący serwer "hello world".
public class Startup
{
public void Configuration(IAppBuilder app)
{
app.Run(context =>
{
context.Response.ContentType = "text/plain";
return context.Response.WriteAsync("Hello World!");
});
}
}
Ten bardzo prosty serwer sieci Web można teraz uruchomić przy użyciu polecenia F5 programu Visual Studio i obejmuje pełną obsługę debugowania.
Przełączanie hostów
Domyślnie poprzedni przykład "hello world" jest uruchamiany w potoku żądania ASP.NET, który używa elementu System.Web w kontekście usług IIS. Może to samo w sobie zwiększyć ogromną wartość, ponieważ pozwala nam korzystać z elastyczności i możliwości komponowania potoku OWIN z możliwościami zarządzania i ogólną dojrzałością usług IIS. Jednak mogą wystąpić przypadki, w których korzyści zapewniane przez usługi IIS nie są wymagane, a pragnienie jest przeznaczone dla mniejszego, bardziej uproszczonego hosta. Co jest potrzebne do uruchomienia naszego prostego serwera sieci Web poza usługami IIS i System.Web?
Aby zilustrować cel przenośności, przejście z hosta serwera sieci Web do hosta wiersza polecenia wymaga po prostu dodania nowego serwera i zależności hosta do folderu wyjściowego projektu, a następnie uruchomienia hosta. W tym przykładzie hostujemy nasz serwer internetowy na hoście Katana o nazwie OwinHost.exe
i użyjemy serwera opartego na składniku Katana HttpListener. Podobnie jak w przypadku innych składników Katana, zostaną one uzyskane z narzędzia NuGet przy użyciu następującego polecenia:
install-package OwinHost
W wierszu polecenia możemy następnie przejść do folderu głównego projektu i po prostu uruchomić OwinHost.exe
plik (który został zainstalowany w folderze tools odpowiedniego pakietu NuGet). Domyślnie OwinHost.exe
program jest skonfigurowany do wyszukiwania serwera opartego na protokole HttpListener i dlatego nie jest wymagana żadna dodatkowa konfiguracja. Nawigowanie w przeglądarce internetowej w celu pokazania http://localhost:5000/
aplikacji uruchomionej teraz za pośrednictwem konsoli.
Architektura Katana
Architektura składnika Katana dzieli aplikację na cztery warstwy logiczne, jak pokazano poniżej: host, serwer, oprogramowanie pośredniczące i aplikacja. Architektura składników jest uwzględniana w taki sposób, że implementacje tych warstw można łatwo zastąpić w wielu przypadkach bez konieczności ponownej kompilacji aplikacji.
Host
Host jest odpowiedzialny za:
Zarządzanie podstawowym procesem.
Organizowanie przepływu pracy, który powoduje wybór serwera i budowy potoku OWIN, za pomocą którego będą obsługiwane żądania.
Obecnie istnieją 3 podstawowe opcje hostingu dla aplikacji opartych na katanie:
IIS/ASP.NET: Przy użyciu standardowych typów HttpModule i HttpHandler potoki OWIN mogą być uruchamiane w usługach IIS w ramach przepływu żądania ASP.NET. ASP.NET obsługa hostingu jest włączona przez zainstalowanie pakietu NuGet Microsoft.AspNet.Host.SystemWeb w projekcie aplikacji internetowej. Ponadto, ponieważ usługi IIS działają zarówno jako host, jak i serwer, rozróżnienie serwera/hosta OWIN jest przeciążone w tym pakiecie NuGet, co oznacza, że w przypadku korzystania z hosta SystemWeb deweloper nie może zastąpić implementacji serwera alternatywnego.
Host niestandardowy: pakiet składników Katana umożliwia deweloperom hostowanie aplikacji we własnym procesie niestandardowym, niezależnie od tego, czy jest to aplikacja konsolowa, usługa systemu Windows itp. Ta funkcja wygląda podobnie do możliwości samodzielnego hostowania udostępnianej przez internetowy interfejs API. Poniższy przykład przedstawia niestandardowy host kodu internetowego interfejsu API:
static void Main()
{
var baseAddress = new Uri("http://localhost:5000");
var config = new HttpSelfHostConfiguration(baseAddress);
config.Routes.MapHttpRoute("default", "{controller}");
using (var svr = new HttpSelfHostServer(config))
{
svr.OpenAsync().Wait();
Console.WriteLine("Press Enter to quit.");
Console.ReadLine();
}
}
Konfiguracja samodzielnego hosta dla aplikacji Katana jest podobna:
static void Main(string[] args)
{
const string baseUrl = "http://localhost:5000/";
using (WebApplication.Start<Startup>(new StartOptions { Url = baseUrl }))
{
Console.WriteLine("Press Enter to quit.");
Console.ReadKey();
}
}
Jedną z istotnych różnic między internetowym interfejsem API i własnym hostem Katana jest brak kodu konfiguracji internetowego interfejsu API w przykładzie samodzielnego hosta Katana. Aby umożliwić przenośność i komponowanie, Katana oddziela kod, który uruchamia serwer od kodu, który konfiguruje potok przetwarzania żądań. Kod, który konfiguruje internetowy interfejs API, następnie jest zawarty w klasie Startup, która jest dodatkowo określona jako parametr typu w pliku WebApplication.Start.
public class Startup
{
public void Configuration(IAppBuilder app)
{
var config = new HttpConfiguration();
config.Routes.MapHttpRoute("default", "{controller}");
app.UseWebApi(config);
}
}
Klasa uruchamiania zostanie omówiona bardziej szczegółowo w dalszej części artykułu. Jednak kod wymagany do uruchomienia procesu samodzielnego hosta Katana wygląda uderzająco podobnie do kodu, który może być używany obecnie w aplikacjach samoobsługowych interfejsu API sieci Web ASP.NET.
OwinHost.exe: Podczas gdy niektórzy chcą napisać proces niestandardowy do uruchamiania aplikacji internetowych Katana, wielu woli po prostu uruchomić wstępnie skompilowany plik wykonywalny, który może uruchomić serwer i uruchomić aplikację. W tym scenariuszu pakiet składników Katana obejmuje element OwinHost.exe
. Po uruchomieniu z katalogu głównego projektu ten plik wykonywalny uruchomi serwer (domyślnie używa serwera HttpListener) i używa konwencji do znajdowania i uruchamiania klasy uruchamiania użytkownika. Aby uzyskać bardziej szczegółową kontrolę, plik wykonywalny udostępnia wiele dodatkowych parametrów wiersza polecenia.
Serwer
Podczas gdy host jest odpowiedzialny za uruchamianie i konserwowanie procesu, w ramach którego działa aplikacja, serwer jest odpowiedzialny za otwarcie gniazda sieciowego, nasłuchiwanie żądań i wysyłanie ich za pośrednictwem potoku składników OWIN określonych przez użytkownika (jak można już zauważyć, ten potok jest określony w klasie startup dewelopera aplikacji). Obecnie projekt Katana obejmuje dwie implementacje serwera:
- Microsoft.Owin.Host.SystemWeb: Jak wspomniano wcześniej, usługi IIS są zgodne z potokiem ASP.NET działa zarówno jako host, jak i serwer. W związku z tym podczas wybierania tej opcji hostingu usługi IIS zarządzają problemami na poziomie hosta, takimi jak aktywacja procesu i nasłuchiwanie żądań HTTP. W przypadku ASP.NET aplikacji internetowych wysyła żądania do potoku ASP.NET. Host Katana SystemWeb rejestruje ASP.NET HttpModule i HttpHandler w celu przechwytywania żądań podczas przepływu przez potok HTTP i wysyłania ich za pośrednictwem potoku OWIN określonego przez użytkownika.
- Microsoft.Owin.Host.HttpListener: Jak wskazuje jego nazwa, ten serwer Katana używa klasy HttpListener .NET Framework do otwierania gniazda i wysyłania żądań do potoku OWIN określonego przez dewelopera. Jest to obecnie domyślny wybór serwera dla interfejsu API samoobsługowego hosta Katana i OwinHost.exe.
Oprogramowanie pośredniczące/struktura
Jak wspomniano wcześniej, gdy serwer akceptuje żądanie od klienta, jest odpowiedzialny za przekazywanie go przez potok składników OWIN, które są określone przez kod uruchamiania dewelopera. Te składniki potoku są nazywane oprogramowaniem pośredniczącym.
Na bardzo podstawowym poziomie składnik oprogramowania pośredniczącego OWIN musi po prostu zaimplementować delegata aplikacji OWIN, aby można było go wywołać.
Func<IDictionary<string, object>, Task>
Jednak w celu uproszczenia opracowywania i tworzenia składników oprogramowania pośredniczącego katana obsługuje kilka konwencji i typów pomocników dla składników oprogramowania pośredniczącego. Najczęstszą z nich jest OwinMiddleware
klasa . Niestandardowy składnik oprogramowania pośredniczącego utworzony przy użyciu tej klasy będzie wyglądać podobnie do następującego:
public class LoggerMiddleware : OwinMiddleware
{
private readonly ILog _logger;
public LoggerMiddleware(OwinMiddleware next, ILog logger) : base(next)
{
_logger = logger;
}
public override async Task Invoke(IOwinContext context)
{
_logger.LogInfo("Middleware begin");
await this.Next.Invoke(context);
_logger.LogInfo("Middleware end");
}
}
Ta klasa pochodzi z OwinMiddleware
klasy , implementuje konstruktor, który akceptuje wystąpienie następnego oprogramowania pośredniczącego w potoku jako jeden z jego argumentów, a następnie przekazuje go do konstruktora podstawowego. Dodatkowe argumenty używane do konfigurowania oprogramowania pośredniczącego są również deklarowane jako parametry konstruktora po następnym parametrze oprogramowania pośredniczącego.
W czasie wykonywania oprogramowanie pośredniczące jest wykonywane za pośrednictwem metody zastępowania Invoke
. Ta metoda przyjmuje jeden argument typu OwinContext
. Ten obiekt kontekstu jest dostarczany przez Microsoft.Owin
opisany wcześniej pakiet NuGet i zapewnia silnie typizowany dostęp do żądania, odpowiedzi i słownika środowiska wraz z kilkoma dodatkowymi typami pomocnika.
Klasę oprogramowania pośredniczącego można łatwo dodać do potoku OWIN w kodzie uruchamiania aplikacji w następujący sposób:
public class Startup
{
public void Configuration(IAppBuilder app)
{
app.Use<LoggerMiddleware>(new TraceLogger());
}
}
Ponieważ infrastruktura Katana po prostu tworzy potok składników oprogramowania pośredniczącego OWIN, a ponieważ składniki muszą po prostu obsługiwać delegata aplikacji, aby uczestniczyć w potoku, składniki oprogramowania pośredniczącego mogą być złożone od prostych rejestratorów po całe struktury, takie jak ASP.NET, internetowy interfejs API lub SignalR. Na przykład dodanie ASP.NET internetowego interfejsu API do poprzedniego potoku OWIN wymaga dodania następującego kodu uruchamiania:
public class Startup
{
public void Configuration(IAppBuilder app)
{
app.Use<LoggerMiddleware>(new TraceLogger());
var config = new HttpConfiguration();
// configure Web API
app.UseWebApi(config);
// additional middleware registrations
}
}
Infrastruktura Katana skompiluje potok składników oprogramowania pośredniczącego na podstawie kolejności, w jakiej zostały dodane do obiektu IAppBuilder w metodzie Configuration. W naszym przykładzie narzędzie LoggerMiddleware może obsługiwać wszystkie żądania, które przepływają przez potok, niezależnie od sposobu obsługi tych żądań. Umożliwia to zaawansowane scenariusze, w których składnik oprogramowania pośredniczącego (np. składnik uwierzytelniania) może przetwarzać żądania potoku zawierającego wiele składników i struktur (np. ASP.NET internetowego interfejsu API, usługi SignalR i statycznego serwera plików).
Aplikacje
Jak pokazano w poprzednich przykładach, projekt OWIN i Katana nie powinien być uważany za nowy model programowania aplikacji, ale raczej abstrakcję do oddzielenia modeli programowania aplikacji i struktur z infrastruktury serwera i hostingu. Na przykład podczas kompilowania aplikacji internetowego interfejsu API platforma deweloperów będzie nadal korzystać z platformy interfejsu API sieci Web ASP.NET niezależnie od tego, czy aplikacja działa w potoku OWIN przy użyciu składników z projektu Katana. Jednym miejscem, w którym kod związany z OWIN będzie widoczny dla dewelopera aplikacji, będzie kod uruchamiania aplikacji, w którym deweloper komponuje potok OWIN. W kodzie uruchamiania deweloper zarejestruje serię instrukcji UseXx, zazwyczaj jedną dla każdego składnika oprogramowania pośredniczącego, która będzie przetwarzać żądania przychodzące. To środowisko będzie miało taki sam efekt jak rejestrowanie modułów HTTP w bieżącym świecie System.Web. Zazwyczaj większe oprogramowanie pośredniczące platformy, takie jak ASP.NET internetowy interfejs API lub SignalR , zostanie zarejestrowane na końcu potoku. Składniki oprogramowania pośredniczącego wycinania krzyżowego, takie jak te do uwierzytelniania lub buforowania, są zwykle rejestrowane na początku potoku, dzięki czemu będą przetwarzać żądania dotyczące wszystkich struktur i składników zarejestrowanych w dalszej części potoku. To oddzielenie składników oprogramowania pośredniczącego od siebie i od podstawowych składników infrastruktury pozwala składnikom rozwijać się w różnych odstępach czasu przy jednoczesnym zapewnieniu, że ogólny system pozostaje stabilny.
Składniki — pakiety NuGet
Podobnie jak wiele bieżących bibliotek i struktur, składniki projektu Katana są dostarczane jako zestaw pakietów NuGet. W przypadku nadchodzącej wersji 2.0 graf zależności pakietu Katana wygląda następująco. (Kliknij obraz, aby wyświetlić większy widok).
Prawie każdy pakiet w projekcie Katana zależy bezpośrednio lub pośrednio od pakietu Owin. Można pamiętać, że jest to pakiet zawierający interfejs IAppBuilder, który zapewnia konkretną implementację sekwencji uruchamiania aplikacji opisanej w sekcji 4 specyfikacji OWIN. Ponadto wiele pakietów zależy od microsoft.Owin, który udostępnia zestaw typów pomocników do pracy z żądaniami HTTP i odpowiedziami. Pozostała część pakietu może być klasyfikowana jako hostowanie pakietów infrastruktury (serwerów lub hostów) lub oprogramowania pośredniczącego. Pakiety i zależności spoza projektu Katana są wyświetlane w kolorze pomarańczowym.
Infrastruktura hostingu dla katana 2.0 obejmuje zarówno serwery oparte na SystemWeb, jak i HttpListener, pakiet OwinHost do uruchamiania aplikacji OWIN przy użyciu OwinHost.exe oraz pakiet Microsoft.Owin.Hosting na potrzeby samodzielnego hostowania aplikacji OWIN na hoście niestandardowym (np. aplikacja konsolowa, usługa systemu Windows itp.)
W przypadku programu Katana 2.0 składniki oprogramowania pośredniczącego koncentrują się głównie na dostarczaniu różnych środków uwierzytelniania. Udostępniono jeden dodatkowy składnik oprogramowania pośredniczącego dla diagnostyki, który umożliwia obsługę strony początkowej i błędu. W miarę rozwoju OWIN w abstrakcji hostingu ekosystem składników oprogramowania pośredniczącego, zarówno tych opracowanych przez firmę Microsoft, jak i innych firm, będzie również rosnąć w liczbie.
Podsumowanie
Od samego początku celem projektu Katana nie było tworzenie i zmuszanie deweloperów do nauki kolejnej struktury internetowej. Zamiast tego celem było utworzenie abstrakcji w celu nadania deweloperom aplikacji internetowych platformy .NET większego wyboru niż wcześniej. Dzieląc logiczne warstwy typowego stosu aplikacji internetowej na zestaw składników możliwych do zastąpienia, projekt Katana umożliwia składnikom w całym stosie poprawę w dowolnej szybkości dla tych składników. Tworząc wszystkie składniki wokół prostej abstrakcji OWIN, Katana umożliwia platformom i aplikacjom opartym na nich przenośnie na różnych serwerach i hostach. Dzięki umieszczeniu dewelopera w kontroli nad stosem, Katana zapewnia, że deweloper dokonuje ostatecznego wyboru na temat tego, jak lekki lub jak bogaty w funkcje powinien być jej stos internetowy.
Aby uzyskać więcej informacji na temat katana
- Projekt Katana w witrynie GitHub: https://github.com/aspnet/AspNetKatana/.
- Wideo: The Katana Project - OWIN for ASP.NET, Howard Dierking.
Podziękowania
- Rick Anderson: (twitter @RickAndMSFT ) Rick jest starszym pisarzem programistycznym dla firmy Microsoft koncentrującym się na platformie Azure i MVC.
- Scott Hanselman: (twitter @shanselman )
- Jon Galloway: (twitter @jongalloway )