ASP.NET Core Blazor 3.1/3.2: Blazor Server und Blazor WebAssembly (E-Book (PDF) + Full-HD-Video (MP4))
ASP.NET Core Blazor 3.1/3.2: Blazor Server und Blazor WebAssembly
Moderne Single-Page-Web-Applications mit .NET, C# und Visual Studio
Über das Buch
Dieses Top-aktuelle Fachbuch (Stand .NET Core-/Blazor Server-Version 3.1 und Blazor WebAssembly 3.2) unterstützt Sie nicht nur beim Einstieg in Blazor, sondern geht auch in vielen technischen Details weit über die spärliche Produktdokumentation hinaus.
Dabei werden beide Formen von Blazor gegenübergestellt: Blazor Server (erstmal erschienen im September 2019) und Blazor Webassembly (erstmals erschienen im Mai 2020). Das Buch thematisiert ausführlich den Unterschied zwischen beiden Architekturen einschließlich Vor- und Nachteilen.
Danach behandelt das Buch alle wichtigen Programmieraufgaben für moderne Webanwendungen: Projektaufbau, Komponenten, Routing, Code-Behind, Ereignisse, Razor-Syntax, Zustandsverwaltung, Komponentenverschachtelung, Formulare/Eingabemasken, Klassenbibliotheken und Razor Class Libraries, Debugging, Dependency Injection (DI), Zugriff auf REST-Dienste, Benachrichtigungen mit ASP.NET Core SignalR, Interoperabilität mit JavaScript, Authentifizierung und Benutzerverwaltung sowie die Umwandlung in eine Progressive Web App (PWA) und die Nutzung als Micro-App.
Im Buch wird das praxisnahe Fallbeispiel "MiracleList" ausführlich behandelt, welches es in zwei Implementierungen sowohl für Blazor WebAssembly als auch Blazor Server zum Download für die Leser gibt. Beide Versionen werden im Buch beschrieben und gegenübergestellt.
Beide Versionen werden im Buch beschrieben und gegenübergestellt. Außerdem bietet das Buch zahlreiche Tipps und Tricks sowie viele Praxishinweise.
Pakete
Nur das E-Book (PDF)
Buch als PDF. Programmcodebeispiele zum Download auf der Leser-Website.
PDF
Deutsch
E-Book (PDF) + Full-HD-Video (MP4)
Buch als PDF und Full-HD-Video zu Blazor (rund 80 Minuten). Programmcodebeispiele zum Download auf der Leser-Website.
PDF
Deutsch
Inhaltsverzeichnis
- 1: Inhaltsverzeichnis Seite 4
- 2: Vorwort Seite 14
- 3: Über den Autor Seite 16
- 4: Über dieses Buch Seite 17
- 4.1: Versionsgeschichte dieses Buchs Seite 17
- 4.2: Bezugsquelle für Aktualisierungen Seite 23
- 4.3: Geplante Kapitel Seite 23
- 4.4: Programmiersprache in diesem Buch Seite 24
- 4.5: Notwendige Vorkenntnisse Seite 24
- 4.6: Aktion "Buch-Abo" Seite 26
- 4.7: Aktion "Buch für Buchrezension" Seite 27
- 5: Programmcodebeispiel zum Download Seite 29
- 5.1: Webadresse für Downloads Seite 29
- 5.2: Übersicht über die Beispiele Seite 29
- 5.3: Eingesetztes CSS-Framework Seite 31
- 5.4: Das Fallbeispiel "MiracleList" Seite 31
- 5.4.1: Szenario Seite 31
- 5.4.2: Technische Basis für MiracleList Seite 31
- 5.4.3: Webadressen Seite 32
- 5.4.4: Projektmappenaufbau Seite 32
- 5.4.5: MiracleList-Bildschirmmasken Seite 33
- 5.5: Beispiele außerhalb des MiracleList-Szenarios Seite 38
- 5.6: Visual Studio 2019 Seite 39
- 5.7: .NET SDK Seite 41
- 5.8: Testen Ihrer PC-Konfiguration Seite 42
- 5.9: Util.Log() Seite 43
- 5.10: Qualitätssicherung der Programmcodebeispiele Seite 43
- 6: Was ist ASP.NET Core Blazor? Seite 45
- 6.1: Blazor-Arten Seite 45
- 6.2: Geschichte von Blazor Seite 47
- 6.3: Technischer Support für Blazor Seite 49
- 6.3.1: Support für Blazor Server Seite 49
- 6.3.2: Support für Blazor WebAssembly Seite 50
- 6.4: Blazor Server Seite 50
- 6.4.1: Rendering und Interaktion bei Blazor Server Seite 50
- 6.4.2: Netzwerkverkehr bei Blazor Server Seite 51
- 6.4.3: Ressourcenbedarf und Skalierbarkeit Seite 52
- 6.4.4: Vor- und Nachteile von Blazor Server Seite 53
- 6.5: Blazor WebAssembly Seite 54
- 6.5.1: Konzept von Blazor WebAssembly Seite 54
- 6.5.2: WebAssembly (WASM) Seite 55
- 6.6: Fehlende Funktionen Seite 57
- 6.7: Ausblick auf Blazor 5.0 Seite 57
- 6.8: Vergleich zwischen Blazor WebAssembly und Blazor Server Seite 58
- 6.8.1: Die wichtigsten Unterschiede Seite 58
- 6.8.2: Browserunterstützung für Blazor Seite 63
- 6.8.3: Performance-Vergleich Seite 64
- 6.8.4: Anwendungsgröße und Startzeiten Seite 69
- 6.8.5: Speicherlimit Seite 72
- 6.8.6: Fazit Seite 74
- 6.9: Blazor im Vergleich zu anderen Spielarten von ASP.NET Core Seite 75
- 6.10: Blazor im Vergleich zu anderen Webframeworks Seite 76
- 7: Projektaufbau Seite 79
- 7.1: Inhalte der Standard-Projektvorlage Seite 79
- 7.2: Blazor-Projekte anlegen Seite 80
- 7.3: Aufbau eines Blazor Server-Projekts Seite 81
- 7.3.1: Ordner und Dateien Seite 81
- 7.3.2: Projektdatei Seite 83
- 7.3.3: Start-Code Seite 83
- 7.3.4: Genauere Fehlermeldungen aktivieren (Detailed Errors) Seite 86
- 7.3.5: Struktur des Seitenaufbaus Seite 87
- 7.4: Aufbau eines Blazor WebAssembly-Projekts Seite 88
- 7.4.1: Ordner und Dateien Seite 92
- 7.4.2: Projektdatei Seite 92
- 7.4.3: Start-Code im Client-Projekt Seite 93
- 7.4.4: Start-Code im Server-Projekt Seite 93
- 7.5: Anlegen einer kompletten mehrschichtigen Projektstruktur mit der .NET CLI Seite 95
- 8: Übersetzung und Debugging Seite 98
- 8.1: Übersetzung Seite 98
- 8.2: Veröffentlichen Seite 99
- 8.3: Start von Blazor-Projekten in Visual Studio Seite 100
- 8.4: Automatische Neukompilierung bei Änderungen Seite 100
- 8.5: Visual Studio-Debugging in Blazor Server-Projekten Seite 101
- 8.6: Visual Studio-Debugging in Blazor WebAssembly-Projekten Seite 102
- 8.7: Browser-Debugging in Blazor WebAssembly Seite 105
- 9: Komponenten (Razor Components) Seite 107
- 9.1: Einsatz von Razor Components Seite 107
- 9.2: Namen für Komponenten Seite 107
- 9.3: Grundkonzepte am Beispiel einer "Hello World"-Komponente Seite 107
- 9.4: Markup-Dateien mit Inline-Code Seite 109
- 9.5: Komponenten mit Code-Behind-Datei Seite 111
- 9.5.1: Code-Behind-Dateien auf Basis von Vererbung Seite 112
- 9.5.2: Code-Behind-Dateien auf Basis von partiellen Klassen Seite 115
- 9.6: Komponenten ohne Markup nur mit Programmcode Seite 118
- 9.7: CSS-Isolation (ab Blazor 5.0) Seite 120
- 9.8: Nicht-visuelle Komponenten Seite 121
- 9.9: Layoutseiten (Masterpages) Seite 124
- 10: Routing und Navigation Seite 126
- 10.1: Routendefinitionen Seite 126
- 10.2: Routen mit Parametern Seite 127
- 10.3: Navigation Seite 129
- 10.3.1: Navigation per -Tag Seite 129
- 10.3.2: URL-Fragmente Seite 129
- 10.3.3: Komponente Seite 130
- 10.3.4: Navigation im Code Seite 131
- 10.4: Auswerten der aktuellen URL Seite 132
- 10.4.1: Fallunterscheidung bei Mehrfachrouten Seite 132
- 10.4.2: Query Strings Seite 133
- 10.4.3: Komplette URL-Auswertung Seite 134
- 10.4.4: Routerkonfiguration Seite 137
- 11: Razor-Syntax Seite 139
- 12: Ereignisbehandlung Seite 144
- 12.1: Komponentenlebenszyklusereignisse Seite 144
- 12.2: Reaktion auf HTML-Ereignisse Seite 145
- 12.3: Eigene Parameter bei HTML-Ereignissen Seite 146
- 12.4: Standardparameter Seite 147
- 12.5: Standardereignisbehandlung unterbinden Seite 150
- 12.6: Ereignisweitergabe unterbinden Seite 151
- 12.7: Komplexe Befehlsfolgen als Ereignisbehandlung Seite 153
- 13: Komponenteneinbettung Seite 154
- 13.1: Einbetten von Razor Components Seite 154
- 13.2: Parameter für eingebettete Razor Components Seite 154
- 13.3: Kaskadierende Parameter Seite 159
- 13.4: Vorlagenbasierte Komponenten (Templated Components) Seite 163
- 13.4.1: Einfache vorlagenbasierte Komponente Seite 163
- 13.4.2: Vorlagenbasierte Komponente mit mehreren Fragmenten Seite 165
- 13.4.3: Datenübergabe an Renderfragment via Kontext Seite 166
- 13.4.4: Komplexe Objekte als Kontext Seite 167
- 13.4.5: Vorlagenbasierte Komponente mit generischem Typparameter Seite 168
- 13.4.6: Verschachtelung von Renderfragmenten Seite 169
- 13.4.7: Standardwerte für Renderfragmente Seite 171
- 13.4.8: Praxislösung: Repeater Seite 172
- 14: Zustandsverwaltung Seite 175
- 14.1: Komponentenzustand Seite 175
- 14.2: Testanwendung: Counter Seite 175
- 14.3: Verlust des Zustandes Seite 176
- 14.4: Bewahrung des Zustandes Seite 178
- 14.5: Sitzungszustand Seite 179
- 14.6: Generischer Sitzungszustand Seite 180
- 14.7: Nutzung des Webbrowserspeichers Seite 182
- 14.7.1: NuGet-Pakete Seite 183
- 14.7.2: Einsatz von Blazored.LocalStorage Seite 183
- 14.7.3: Verschlüsselter Browserspeicher (Protected Browser Storage) Seite 187
- 14.8: Cookies Seite 190
- 14.9: Persistierung in Datenbanken oder anderen persistenten Speichern auf dem Server Seite 192
- 15: Formulare/Eingabemasken Seite 193
- 15.1: Formulare auf Basis der Blazor-Eingabekomponenten Seite 193
- 15.1.1: Verfügbare Blazor-Eingabekomponenten Seite 193
- 15.1.2: Komponente Seite 194
- 15.1.3: Datenbindung Seite 195
- 15.1.4: Datenannotationen Seite 195
- 15.1.5: Validierungskomponenten in Blazor Seite 197
- 15.1.6: Eigene Validierungsannotationen Seite 197
- 15.1.7: Beispiel Seite 198
- 15.1.8: Optionsfelder Seite 203
- 15.2: Formulare auf Basis von Standard-HTML-Tags Seite 205
- 15.2.1: Datenbindung Seite 205
- 15.2.2: Reaktion auf einzelne Buchstabeneingaben Seite 206
- 15.2.3: Datenbindung mit Datumsangaben Seite 211
- 15.2.4: Praxisbeispiel Seite 214
- 15.2.5: Fokus setzen Seite 218
- 16: Razor Class Libraries (RCL) Seite 220
- 16.1: .NET Standard Seite 220
- 16.2: Referenzierbarkeit Seite 222
- 16.3: Anlegen der Klassenbibliotheken Seite 222
- 16.4: Einsatzgebiete der verschiedenen Klassenbibliotheksarten Seite 224
- 16.5: Razor Class Libraries (RCL) Seite 224
- 16.5.1: Erstellen einer Razor Class Library Seite 224
- 16.5.2: Inhalte einer Razor Class Library Seite 226
- 16.5.3: Referenzierung einer Razor Class Library Seite 226
- 16.5.4: Einbettung von Razor Components aus einer Razor Class Library Seite 229
- 16.5.5: Routing zu Razor Components aus einer Razor Class Library Seite 229
- 16.5.6: Nutzung von statischen Ressourcen aus einer Razor Class Library Seite 230
- 16.6: Lazy Loading von DLLs (ab Blazor 5.0) Seite 231
- 16.7: Code-Sharing zwischen Blazor Server und Blazor WebAssembly Seite 234
- 17: Dependency Injection (DI) Seite 236
- 17.1: Microsoft.Extensions.DependencyInjection Seite 236
- 17.2: Implementierung eines Dienstes Seite 236
- 17.3: Lebensdauer von Instanzen Seite 237
- 17.4: Registrierung von Diensten Seite 239
- 17.5: Injektion in einen Konstruktor (Konstruktorinjection) Seite 239
- 17.6: Automatisch registrierte Dienste Seite 240
- 17.7: Manuelle Beschaffung Seite 240
- 17.8: Injektion in eine Razor Components Seite 240
- 17.9: Injezierung in Properties mit [Inject] Seite 241
- 18: Interoperabilität mit JavaScript Seite 242
- 18.1: Aufruf von .NET zu JavaScript Seite 242
- 18.2: Eigene JavaScript-Dateien verwenden. Seite 244
- 18.3: Aufruf von JavaScript zu .NET (statische Methoden) Seite 246
- 18.4: Aufruf von JavaScript zu .NET (Instanzmethoden) Seite 250
- 18.5: Praxisbeispiel: Nutzung einer vorhandenen JavaScript-Bibliothek Seite 251
- 19: Zugriff auf Webservices/WebAPIs Seite 255
- 19.1: Szenario Seite 255
- 19.2: WebAPI-Dienste Seite 256
- 19.2.1: WebAPIs erstellen mit ASP.NET Core Seite 256
- 19.2.2: WebAPIs testen mit Postman Seite 258
- 19.2.3: Blazor-Zugriff auf Web APIs Seite 258
- 19.2.4: Cross-Origin Resource Sharing für das WebAPI Seite 261
- 19.2.5: Metadaten mit Open API Specification Seite 261
- 19.2.6: Client-Generierung aus Metadaten Seite 262
- 19.3: Google RPC-Dienste Seite 264
- 19.3.1: gRPC-Dienst erstellen Seite 264
- 19.3.2: Blazor-Zugriff auf gRPC-Dienste Seite 268
- 19.4: Leistungsvergleich zwischen WebAPI und gRPC Seite 269
- 19.5: Windows Communication Foundation (WCF) Seite 270
- 20: Benachrichtigungen mit ASP.NET Core SignalR in Blazor Seite 272
- 20.1: Implementierung im Webserver Seite 273
- 20.2: Implementierung im Blazor-Client Seite 274
- 20.3: Aktivieren der Websockets-Unterstützung Seite 278
- 20.4: Diagnose von ASP.NET Core SignalR Seite 280
- 21: Serversystem- und Browserinformationen Seite 281
- 21.1: HttpContext Seite 281
- 21.2: Allgemeine Systeminformationen Seite 283
- 22: Authentifizierung und Benutzerverwaltung Seite 288
- 22.1: Verwenden von ASP.NET Core Identity in Blazor Server Seite 288
- 22.1.1: Aktivieren der Authentifizierung in Blazor Server Seite 288
- 22.1.2: Individuelle Benutzerkontenverwaltung Seite 289
- 22.1.3: Anpassung der Benutzerverwaltungsseiten Seite 291
- 22.1.4: Weitere Anpassung von ASP.NET Identity Seite 295
- 22.2: Authentifizierung in Blazor WebAssembly Seite 295
- 22.2.1: OIDC-Authentifizierung bei Projekten ohne "ASP.NET Core Hosted" Seite 296
- 22.2.2: Weitere OIDC-Optionen Seite 300
- 22.2.3: Authentifizierung bei Projekten mit "ASP.NET Core Hosted" Seite 300
- 22.3: Eigene Authentifizierungsprovider Seite 304
- 22.3.1: AuthenticationStateProvider für Debugging-Zwecke Seite 305
- 22.3.2: AuthenticationStateProvider in MiracleList Seite 306
- 22.3.3: Nutzung des eigenen AuthenticationStateProvider Seite 313
- 22.4: Zugriff auf den angemeldeten Benutzer Seite 314
- 22.5: Autorisierung Seite 315
- 22.5.1: Autorisierung von Komponenten Seite 315
- 22.5.2: Inhalte für angemeldete Benutzer Seite 316
- 22.5.3: Umleitung für nicht-autorisierte Benutzer Seite 316
- 23: Installation von Blazor-Anwendungen Seite 318
- 23.1: Deployment Seite 318
- 23.2: Installation auf Azure-Diensten Seite 319
- 23.2.1: WebSockets Seite 319
- 23.2.2: Brotli-Komprimierung Seite 320
- 23.3: Installationsvoraussetzungen für eigene Windows-Webserver (IIS) Seite 321
- 23.4: Installation auf einem eigenen Windows-Webserver (IIS) Seite 322
- 23.5: Self-Hosting (Kestrel Webserver) Seite 326
- 24: Tipps, Tricks und Tools Seite 328
- 24.1: Ermitteln der Blazor-Art und -Versionsnummer Seite 328
- 24.2: Ausgaben in die Browserkonsole Seite 330
- 24.3: BlazorFiddle Seite 334
- 24.4: Fortschrittsanzeige Seite 335
- 24.5: Countdown mit Zeitgeber (Timer) Seite 337
- 24.6: Eigene Timer-Komponente für Blazor Seite 338
- 24.7: Meldungskomponente Seite 339
- 24.8: Toast-Benachrichtigungen Seite 344
- 24.9: Zugriff auf die lokale Zeit des Webbrowsers Seite 345
- 24.10: Custom Boot Resource Loading Seite 346
- 24.11: Progressive Web Applications (PWA) mit Blazor WebAssembly Seite 346
- 24.12: Verzögerter Start einer Blazor WebAssembly-Anwendung Seite 351
- 24.13: Integration von Blazor-Anwendungen in andere Webanwendungen Seite 352
- 24.14: Micro-Apps mit Blazor Seite 353
- 24.14.1: Projektaufbau Seite 354
- 24.14.2: Kommunikation Seite 356
- 25: Fallbeispiel "MiracleList" Seite 360
- 25.1: Das MiracleList-Backend Seite 360
- 25.1.1: Softwarearchitektur Seite 363
- 25.1.2: Entitätsklassen Seite 366
- 25.1.3: Entity Framework Core-Kontextklasse Seite 368
- 25.1.4: Lebensdauer der Kontextklasse in ASP.NET Core-Anwendungen Seite 369
- 25.1.5: Geschäftslogik Seite 370
- 25.1.6: Web API Seite 379
- 25.2: MiracleList-Frontend mit Blazor Server Seite 389
- 25.2.1: Softwarearchitektur Seite 389
- 25.2.2: Startcode (Program.cs und Startup.cs) Seite 392
- 25.2.3: Startseite (_Host.cshtml) Seite 395
- 25.2.4: Anmeldeansicht (Login.razor) Seite 396
- 25.2.5: Authentication State Provider (MLAuthenticationStateProvider) Seite 400
- 25.2.6: Hauptansicht (Index.razor) Seite 404
- 25.2.7: Bearbeitungsformular (TaskEdit.razor) Seite 410
- 25.3: MiracleList-Frontend mit Blazor WebAssembly Seite 412
- 25.3.1: Softwarearchitektur Seite 412
- 25.3.2: Projektdatei Seite 415
- 25.3.3: Startseite mit Ladeanimation (index.html) Seite 416
- 25.3.4: Blazor WebAssembly-Startcode (Program.cs) Seite 417
- 25.3.5: Anmeldeansicht (Login.razor) Seite 418
- 25.3.6: Authentication State Provider (MLAuthenticationStateProvider) Seite 422
- 25.3.7: Hauptansicht (Index.razor) Seite 425
- 25.3.8: Bearbeitungsformular (TaskEdit.razor) Seite 429
- 26: Umstieg von ASP.NET Webforms zu ASP.NET Core Blazor Seite 432
- 26.1: Migrationspfade und Herausforderungen Seite 432
- 26.2: Grundsätzliche Vorgehensweise bei der Migration Seite 434
- 26.3: Umstieg von Webforms auf Blazor an einem Beispiel Seite 435
- 26.3.1: Umsetzung der Datentabelle mit Webforms und Blazor Seite 436
- 26.3.2: Umstellung der Benutzerschnittstellenbeschreibung Seite 442
- 26.3.3: Umstellung der Benutzerschnittstellensteuerung Seite 443
- 26.4: Einsatz von Telerik UI for Blazor Seite 444
- 26.4.1: Komponenten in Telerik UI for Blazor Seite 444
- 26.4.2: Bezugsquelle und Preise Seite 444
- 26.4.3: Installation von Telerik UI for Blazor Seite 445
- 26.4.4: Erstellen eines Projekts mit Telerik UI for Blazor Seite 447
- 26.4.5: Integration von Telerik UI for Blazor in bestehende Blazor-Projekte Seite 450
- 26.4.6: Umsetzung der Flugdatentabelle mit Telerik UI for Blazor Seite 451
- 26.5: Einsatz von DevExpress UI for Blazor Seite 457
- 26.5.1: Komponenten in DevExpress UI for Blazor Seite 457
- 26.5.2: Bezugsquelle und Preise Seite 458
- 26.5.3: Installation von DevExpress UI for Blazor Seite 459
- 26.5.4: Erstellen eines Projekts mit DevExpress UI for Blazor Seite 460
- 26.5.5: Umsetzung der Flugdatentabelle mit DevExpress UI for Blazor Seite 462
- 27: Mobile Apps mit Mobile Blazor Bindings Seite 469
- 27.1: Architektur der Mobile Blazor Bindings Seite 469
- 27.2: Versionsgeschichte Seite 470
- 27.3: Projekt anlegen Seite 470
- 27.4: Übersetzung und Debugging für Android Seite 471
- 27.5: Aufbau der Projektvorlage Seite 473
- 27.6: Verfügbare Steuerelemente Seite 474
- 28: Quellen im Internet Seite 476
- 29: Stichwortverzeichnis (Index) Seite 477
- 30: Werbung in eigener Sache Seite 486
Andere Bücher dieses Autors
Die bedingungslose Leanpub Garantie: Kein Risiko, 100% Zufriedenheit
Innerhalb von 60 Tagen ab Kauf kannst du dein Geld zu 100% zurückverlangen, bei jedem Leanpub-Kauf, in nur zwei Klicks. Wir bearbeiten die Erstattungen manuell, daher dauert es ein paar Tage, bis der Betrag ankommt.
Lese die kompletten Bedingungen.
Verdienen Sie $8 bei einem Kauf von $10 und $16 bei einem Kauf von $20
Wir zahlen 80% Tantiemen bei Käufen von $7,99 oder mehr und 80% Tantiemen abzüglich einer Pauschalgebühr von 50 Cent bei Käufen zwischen $0,99 und $7,98. Sie verdienen $8 bei einem Verkauf von $10 und $16 bei einem Verkauf von $20. Wenn wir also 5000 nicht zurückgegebene Exemplare Ihres Buches für $20 verkaufen, verdienen Sie $80,000.
(Ja, einige Autoren haben auf Leanpub bereits viel mehr verdient.)
Tatsächlich haben Autoren durch das Schreiben, Veröffentlichen und Verkaufen auf Leanpubüber 13 Millionen Dollar verdient.
Erfahren Sie mehr über das Schreiben auf Leanpub
Kostenlose Updates. Ohne DRM.
Mit dem Kauf auf Leanpub bekommst Du kostenlose Updates solange der Autor Änderungen vornimmt! Viele Autoren veröffentlichen ihre Bücher während des Schreibens. Alle Leser bekommen dann kostenlose Updates, egal wann sie das Buch gekauft haben oder wie viel sie bezahlt haben (auch wenn es kostenlos war).
Die meisten Leanpub Bücher sind erhältlich als PDF (für Computer) oder EPUB (für Handy, Tablet, Kindle). Die verfügbaren Formate sind oben rechts auf dieser Seite angezeigt.
Leanpub Bücher kommen ohne DRM Kopierschutz Firlefanz, sodass Du sie problemlos auf jedem unterstützten Gerät lesen kannst.
Erfahren Sie mehr über Leanpubs E-Book-Formate und wo Sie sie lesen können