Quo vadis, .NET?

9. Januar 2020

Microsoft krempelt die .NET-Welt gerade kräftig um. Neue Begriffe, die man noch nicht einordnen kann, Gerüchte um Abkündigungen (die nicht zutreffen!), und die Frage, was das alles konkret bedeutet, sind die logische Folge.

Um zu verstehen, was da gerade passiert – und warum – lohnt sich ein Blick in die Vergangenheit.

Blick in die Vergangenheit

.NET wurde als Preview auf der PDC 2000 vorgestellt. In den ca. 15 Jahren danach war die Entwicklung von zwei Aspekten geprägt: Neue Features und neue Umgebungen.

Neue Features

.NET hatte in diesen ersten 15 Jahren mit jeder neuen Version neue Themen im Gepäck. Der folgende Zeitstrahl gibt das wieder:

image

Angefangen mit .NET 4.6 hat das nachgelassen, Neuerungen sind seit dem eher “Modellpflege”.

Neue Umgebungen

Microsoft hat von Anfang an versucht, .NET zu standardisieren (erste Gehversuche bzgl. Offenheit) und auf verschiedenen Umgebungen zu unterstützen. Die eigene Referenzimplementierung unter FreeBSD, sowie Mono als Open Source-Variante kamen sehr früh.

Aber auch auf den eigenen Plattformen gab es Varianten wie das Micro– und Compact Framework, sowie Silverlight für Web und Windows Phone:

image

Gemeinsam ist diesen Varianten, dass sie keine Relevanz mehr haben.

Die Ausnahme ist Mono/Xamarin: Nachdem Mono lange vor sich hingedümpelt ist, bekam es mit der Übernahme durch Xamarin und der Unterstützung der wichtigsten Mobile Plattformen einen deutlichen Schub. Und mit der Übernahme durch Microsoft kamen macOS, Android und iOS auf die Liste der direkt von Microsoft unterstützten Betriebssysteme. Parallel dazu hatte Microsoft mit .NET Core selbst angefangen, Linux-Varianten zu unterstützen.

image

Der Preis des Erfolgs

Als .NET auf der PDC 2000 vorgestellt wurde, gab es Standing Ovations, weil .NET viele der Probleme der bis dato vorherrschenden Entwicklung mit Visual Basic, C++ und COM einfach beiseite wischte. 10 bis 15 Jahre später begann .NET am eigenen Erfolg zu kränkeln.

Ein Problem bestand für Entwickler von Bibliotheken: Assemblies waren – bei nahezu identischem Code auf allen Plattformen – immer auf genau eine Plattform festgelegt. Wer eine allgemeingültige Bibliothek bereitstellen wollte – etwa ein Logging-Framework wie log4net oder ein Dependency Injection Framework –, der musste dies für jede Plattform separat tun. Und spätestens mit dem Aufkommen von Xamarin und plattformübergreifender Entwicklung waren davon zunehmend auch Anwendungsentwickler betroffen.

Der Lösungsansatz für dieses Problem waren Portable Class Libraries (PCL): Assembly-Projekte konnten angeben, für welche Plattformen sie verfügbar sein sollten. Die Compiler-Infrastruktur stellte sicher, dass man nur auf die Funktionen zugreifen konnte, die auf allen diesen Plattformen verfügbar sind. Einerseits konnte man dadurch mit einem Assembly mehrere Plattformen bedienen, andererseits wurde die Menge der verfügbaren Funktionen mit jeder zusätzlichen Plattform kleiner.

Als rein technischer Lösungsansatz haben PCLs ihre Aufgabe durchaus erfüllt. In der Praxis ist aber die Schnittmenge der verfügbaren Funktionen eine deutliche Einschränkung – PCLs müssen eigentlich immer um plattformabhängige Assemblies ergänzt werden. Das führte dazu, dass PCLs eine Nischenlösung blieben.

Andere Problembereiche ergaben sich durch den Umfang und die Verbreitung von .NET selbst. Fortschritte im Bereich der Compiler-Technologie ließen sich nicht nutzen, weil dies in einigen Fällen zu Inkompatibilitäten geführt hätte. Das globale Deployment erwies sich als Hemmschuh, wenn es um kleine Windows Store Anwendungen ging. Die enge Bindung mit Laufzeitumgebungen wie dem IIS für ASP.NET, sowie das Mitschleifen längst abgekündigter Konzepte wie Code Access Security taten ein Übriges, um der Weiterentwicklung Fußfesseln anzulegen.

Blick in die Gegenwart

Das war die Situation vor ca. 5 Jahren: Ein sehr erfolgreiches .NET Framework, das sich für die Weiterentwicklung als Hemmschuh herausstellte; mit PCLs eine technische Lösung, die einiges zu wünschen übrig ließ; und nicht zuletzt geänderte Anforderungen, die mit den “traditionellen” .NET-Umgebungen nicht adäquat zu beantworten waren. Mit .NET Core schlug Microsoft daher neue Wege ein.

.NET Core

.NET Core ist ursprünglich für Windows Store Apps entstanden: Ein radikal entschlacktes .NET, Dinge wie AppDomains oder Remoting entfernt, das Deployment-Modell so geändert, dass jede Anwendung ihr eigenes .NET mitbringt. So entstand eine schlanke kleine Laufzeitumgebung, die vollständig in einer Store App installiert werden konnte, ohne dass sie andere Installationen voraussetzte oder diese beeinflusste.

Dadurch konnten nicht nur neue Compiler-Technologien wie der 64-bit-Compiler RyuJIT oder .NET Native leichter umgesetzt werden, zudem verringerte sich auch die Abhängigkeit von Windows, so dass sich die Entwicklung von .NET Core sehr schnell in den Bereich von ASP.NET Core und Container-Technologien verlagerte.

Dieses Vorgehen löste das Problem der Altlasten; das Problem für Bibliotheksentwickler hätte aber weiter bestanden.

.NET Standard

Microsoft hätte .NET Core als eine weitere Plattform in PCL aufzunehmen können, aber auch hier haben sie sich – zum Glück! – anders entschieden: Anstatt sich der eingeschränkten Schnittmenge verfügbarer Funktionen zu beugen – mit mehr oder weniger großen Lücken und Inkonsistenzen – haben sie definiert, welche Funktionen sie gerne hätten. Eine einzige, vollständige, konsistente API, unabhängig von der Plattform. Der Name dieser Definition: .NET Standard.

Und jede Plattform, die konform zu .NET Standard sein will, muss entsprechend nacharbeiten, wenn Funktionen fehlen. Dies ist mittlerweile für alle noch relevanten Plattformen geschehen, so dass ein .NET Standard-Assembly auch auf allen diesen Plattformen eingesetzt werden kann:

image
Quelle: https://dotnet.microsoft.com/platform/dotnet-standard

In .NET Standard enthalten sind die Basisfeatures, die die Laufzeitumgebungen bereitstellen müssen:

image
vgl. https://devblogs.microsoft.com/dotnet/introducing-net-standard/

Microsoft Extensions

Im Zuge der Entwicklung an .NET Core, insbesondere an ASP.NET Core, kristallisierten sich weitere Themen heraus, die zwar nicht von der Plattform selbst zur Verfügung gestellt werden müssen, aber die aus Sicht eines Anwendungsentwicklers genauso grundlegend sind. Dinge wie Konfiguration, Logging oder Dependency Injection.

Microsoft hat diese Blöcke als .NET Standard-Bibliotheken unter dem Label “Microsoft Extensions” zur Verfügung gestellt. Also nicht als inhärenten Teil von .NET, wie das zum Beispiel bei System.Configuration der Fall ist, sondern als frei wählbare NuGet-Pakete, die zudem im Quelltext verfügbar sind.

Enthalten sind im Wesentlichen folgende Blöcke:

image

Der Umfang von .NET Standard, ergänzt um die Microsoft Extensions, stellt Anwendungsentwicklern eine solide Grundlage für die Entwicklung zur Verfügung, die auf allen Plattformen nutzbar ist.

Blick in die Zukunft

Kommen wir zum bislang letzten Akt, der im Mai 2019 mit einem Blogbeitrag eingeläutet wurde: .NET 5.

Mit .NET Framework, Mono/Xamarin und .NET Core hat Microsoft nach wie vor drei relevante .NET-Plattformen im Angebot. Drei Plattformen, die gepflegt und weiterentwickelt werden wollen? Die sich gerade auseinanderentwickeln? Wäre es nicht besser, nur eine Plattform pflegen zu müssen?

Das klassische .NET Framework bietet sich dafür nicht an; die Probleme damit haben schließlich zur Abspaltung von .NET Core geführt. Andererseits gibt es hier eine enorme Code-Basis, eine Abkündigung wie seinerzeit mit Silverlight kommt also nicht in Frage.

Die Lösung, die Microsoft sich ausgedacht hat, ist zweigleisig:

Erstens: .NET Framework wird in der Version 4.8 eingefroren und als Betriebssystemkomponente deklariert. Niemand muss bestehende Anwendungen migrieren, aber Weiterentwicklungen in .NET kommen eben auch nur den anderen Plattformen zugute.

Zweitens: In .NET Core 3.0 werden die Bestandteile verfügbar gemacht, die Entwickler bislang vom Einsatz von .NET abgehalten haben: Im Wesentlichen Windows Forms und WPF. Für neue Anwendungen gibt es also – so die Hoffnung – keinen Grund noch auf das klassische .NET Framework zu setzen.

Ob diese Hoffnung sich bestätigt ist keineswegs sichergestellt. Größter Stolperstein dabei ist WCF, das unter .NET Core bzw. .NET Standard nicht voll verfügbar ist. Im Web- oder Cloud-Umfeld ist das kein Problem, aber im Unternehmensumfeld ist WCF sehr verbreitet. Und auch Remoting oder die Workflow Foundation haben ihre Nische.

Dieser Schritt ist vollbracht: .NET Core 3.0 ist verfügbar und 3.1 in Preview (Stand November 2019).
Bleiben noch die beiden Umgebungen Mono/Xamarin und .NET Core. Deren Zusammenführung ist der Kern der Ankündigung:

.NET 5 builds on this work, taking .NET Core and the best of Mono to create a single platform that you can use for all your modern .NET code.

Das folgende Diagramm zeigt die Zusammenhänge auf:

image

Ziel dieser Verschmelzung der beiden Laufzeitumgebungen ist eine einzige Umgebung, die dann auf allen Geräten verfügbar ist:


Quelle: https://devblogs.microsoft.com/dotnet/introducing-net-5/

Von der Zusammenführung abgesehen hat Microsoft angekündigt, in welcher Kadenz weitere Versionen erscheinen sollen:


Quelle: https://devblogs.microsoft.com/dotnet/introducing-net-5/

Für .NET Core-Entwickler wird .NET 5 also nur die nächste Version ihrer Laufzeitumgebung sein, eventuell um Features aus Mono ergänzt; für Xamarin-Entwickler gilt analog das gleiche.

Darüberhinausgehende Aussagen, was für die nachfolgenden Versionen geplant ist, gibt es derzeit aber nicht.

Fazit

Für das .NET Framework ist die Bilanz gemischt. Einerseits wurde es zur Betriebssystemkomponente aufgewertet, es gibt also keinen Migrationszwang. Andererseits wird .NET Framework von zukünftigen Weiterentwicklungen ausgeschlossen, der Migrationsdruck wird also über kurz oder lang zunehmen.

Die Entwicklung von .NET Core, .NET Standard und den Microsoft Extensions ist für Anwendungsentwickler eine gute Sache. Eine schlankere, performante Umgebung, Konzepte die den heute doch etwas anders gelagerten Anforderungen gerecht werden. Nicht zuletzt lassen sich .NET Standard und die Microsoft Extensions auch in klassischen .NET Framework-Anwendungen nutzen – sei es wegen der Features selbst, oder in Vorbereitung auf eine angedachte Migration.

Und .NET 5, die große Ankündigung vom Mai? Für Microsoft ist .NET 5 sicher eine wichtige Sache. Aus Sicht von uns Anwendungsentwicklern aber eher nicht. .NET 5 wird einfach die nächste Version von Mono/Xamarin und .NET Core. Nicht mehr als ein technisches Release, denn im Idealfall sollten wir davon nichts merken.

Und was die nachfolgenden Versionen bringen werden, steht noch in den Sternen. Vielleicht überdenkt Microsoft die Entscheidung, WCF nicht zu migrieren, ja doch noch…?

autor Alexander Jung

Alexander Jung

Chief eXpert Alexander.Jung@sdx-ag.de