{"id":23849,"date":"2025-04-11T16:42:08","date_gmt":"2025-04-11T16:42:08","guid":{"rendered":"https:\/\/www.europesays.com\/de\/23849\/"},"modified":"2025-04-11T16:42:08","modified_gmt":"2025-04-11T16:42:08","slug":"net-10-0-preview-3-bringt-typ-erweiterungen","status":"publish","type":"post","link":"https:\/\/www.europesays.com\/de\/23849\/","title":{"rendered":".NET 10.0 Preview 3 bringt Typ-Erweiterungen"},"content":{"rendered":"<ol class=\"a-toc__list\">\n<li class=\"a-toc__item&#10;          &#10;            a-toc__item--counter&#10;          &#10;            a-toc__item--current\">\n<p>              .NET 10.0 Preview 3 bringt Typ-Erweiterungen <\/p>\n<\/li>\n<\/ol>\n<p>.NET 10.0 Preview 3 steht seit gestern zum Download <a href=\"https:\/\/dotnet.microsoft.com\/en-us\/download\/dotnet\/10.0\" rel=\"external noopener nofollow\" target=\"_blank\">auf der .NET-Downloadseite bereit<\/a> bereit. Als Entwicklungsumgebung braucht man dazu wie bisher Visual Studio 17.14 Preview 2.0. Dazu gab es gestern kein Update, was dazu f\u00fchrt, dass man die neuen Sprachfeatures aus .NET 10.0 Preview 3 in Visual Studio noch nicht \u00fcbersetzen kann, da Visual Studio <a href=\"https:\/\/github.com\/dotnet\/roslyn\/blob\/main\/docs\/Language%20Feature%20Status.md\" rel=\"external noopener nofollow\" target=\"_blank\">laut C# Language Feature Status<\/a> diese erst ab Preview 3.0 kennen wird. Beim Bearbeiten in Visual Studio Code und bei der \u00dcbersetzung per Kommandozeilenbefehl dotnet build funktionieren die neuen Features aber bereits.<\/p>\n<p>    <img loading=\"lazy\" decoding=\"async\" alt=\"\" height=\"293\" src=\"data:image\/svg+xml,%3Csvg xmlns='http:\/\/www.w3.org\/2000\/svg' width='696px' height='391px' viewBox='0 0 696 391'%3E%3Crect x='0' y='0' width='696' height='391' fill='%23f2f2f2'%3E%3C\/rect%3E%3C\/svg%3E\" style=\"aspect-ratio: 233 \/ 293; object-fit: cover;\" width=\"233\"\/><\/p>\n<p class=\"a-inline-textbox__synopsis\">\n          Dr. Holger Schwichtenberg ist Chief Technology Expert bei der MAXIMAGO-Softwareentwicklung. Mit dem Expertenteam bei www.IT-Visions.de bietet er zudem Beratung und Schulungen im Umfeld von Microsoft-, Java- und Webtechniken an. Er h\u00e4lt Vortr\u00e4ge auf Fachkonferenzen und ist Autor zahlreicher Fachb\u00fccher.&#13;<\/p>\n<p>      <a href=\"https:\/\/www.heise.de\/imgs\/18\/4\/8\/3\/6\/1\/3\/4\/image1-380c4439bf7e9a70.png\" rel=\"nofollow noopener\" target=\"_blank\"><\/p>\n<p>  <img loading=\"lazy\" decoding=\"async\" alt=\"Das Installationsprogramm zeigt die Bestandteile des .NET 10.0 Preview 3 SDK (Abb. 1)\" height=\"842\" src=\"data:image\/svg+xml,%3Csvg xmlns='http:\/\/www.w3.org\/2000\/svg' width='696px' height='391px' viewBox='0 0 696 391'%3E%3Crect x='0' y='0' width='696' height='391' fill='%23f2f2f2'%3E%3C\/rect%3E%3C\/svg%3E\" style=\"aspect-ratio: 1131 \/ 842; object-fit: cover;\" width=\"1131\"\/><\/p>\n<p>      <\/a><\/p>\n<p>Das Installationsprogramm zeigt die Bestandteile des .NET 10.0 Preview 3 SDK (Abb. 1).<\/p>\n<p class=\"a-caption__source\">\n      (Bild:\u00a0Screenshot (Holger Schwichtenberg))\n    <\/p>\n<p>Extensions-Bl\u00f6cke in C# 14.0<\/p>\n<p>Die nachtr\u00e4gliche Erweiterbarkeit von Klassen, auch wenn diese bereits andernorts kompiliert sind (zum Beispiel in den von Microsoft gelieferten Klassen in den .NET-Klassenbibliotheken), um zus\u00e4tzliche Methoden gibt es unter dem Namen &#8222;Extension Methods&#8220; seit C#-Sprachversion 3.0. Diese erschien zusammen mit .NET Framework 3.5 im Jahr 2007. Man konnte dabei aber nur Instanzmethoden erg\u00e4nzen. So musste man zwangsweise Konstrukte, die vom Namen her Properties waren, leidigerweise als Methoden ausdr\u00fccken, siehe IsEmptyClassic() in Listing 1:<\/p>\n<p>public static class StringExtensionClassic<br \/>\n{<br \/>\n   public static string TruncateClassic(this string s, int count)<br \/>\n   {<br \/>\n      if (s == null) return &#8222;&#8220;;<br \/>\n      if (s.Length  String.IsNullOrEmpty(s);<br \/>\n}<\/p>\n<p>Listing 1: Klassische Extension Methods<\/p>\n<p>In C# 14.0 gibt es nun mit dem neuen Block-Schl\u00fcsselwort extension eine verallgemeinerte M\u00f6glichkeit der Erweiterung bestehender .NET-Klassen. Das Schl\u00fcsselwort extension muss Teil einer statischen, nicht-generischen Klasse auf der obersten Ebene sein (also keine Nested Class). Nach dem Schl\u00fcsselwort extension deklariert man den zu erweiternden Typ, in Listing 2 die Klasse System.String (alternativ abgek\u00fcrzt durch den eingebauten Typ string). Alle Methoden und Properties innerhalb des Extension-Blocks erweitern dann den hier genannten Typen. Aktuell kann man in diesen Extension-Bl\u00f6cken folgende Konstrukte verwenden (siehe Listing 2):<\/p>\n<ul class=\"rte__list rte__list--unordered\">\n<li>Instanz-Methoden<\/li>\n<li>Statische Methoden<\/li>\n<li>Instanz-Properties mit Getter<\/li>\n<li>Statische Properties mit Getter<\/li>\n<\/ul>\n<p>Beim Versuch, einer Property einen Setter zu geben, meckert der Compiler leider mit der unzutreffenden Meldung &#8222;Extension declarations can include only methods or properties&#8220;.<\/p>\n<p>OrderedDictionary websites = new OrderedDictionary();<br \/>\nwebsites.Add(&#8222;Heise&#8220;, &#8222;www.Heise.de&#8220;);<br \/>\nwebsites.Add(&#8222;Microsoft&#8220;, &#8222;www.Microsoft.com&#8220;);<br \/>\nwebsites.Add(&#8222;IT-Visions&#8220;, &#8222;www.IT-Visions.de&#8220;);<\/p>\n<p>var propertyName = &#8222;IT-Visions&#8220;;<br \/>\nvar value = &#8222;www.IT-Visions.de&#8220;;<\/p>\n<p>\/\/ bisher<br \/>\nif (!websites.TryAdd(propertyName, value))<br \/>\n{<br \/>\n  int index1 = websites.IndexOf(propertyName); \/\/ Second lookup operation<br \/>\n  CUI.Warning(&#8222;Element &#8220; + value + &#8220; ist bereits vorhanden!&#8220;);<br \/>\n}<\/p>\n<p>\/\/ neu<br \/>\nif (!websites.TryAdd(propertyName, value, out int index))<br \/>\n{<br \/>\n  CUI.Warning(&#8222;Element &#8220; + value +<br \/>\n              &#8220; ist bereits vorhanden an der Position &#8220; +<br \/>\n              index + &#8222;&#8220;&#8220;!&#8220;&#8220;&#8220;);<br \/>\n}<\/p>\n<p>\/\/ neu<br \/>\nif (websites.TryGetValue(propertyName, out string? value2, out int index2))<br \/>\n{<br \/>\n  CUI.Success($&#8220;Element {value2} wurde gefunden an der Position {index2}.&#8220;);<br \/>\n}<\/p>\n<p>Listing 2: Extension f\u00fcr System.String mit C# 14.0<\/p>\n<p>Listing 3 zeigt den Aufruf der alten und neuen Erweiterungen. Entwicklerinnen und Entwickler haben nun die Wahl, f\u00fcr Extension Methods die alte oder die neue Syntax zu verwenden. Visual Studio wird Refactoring-Methoden zur Umwandlung zwischen beiden Syntaxformen anbieten. Zudem plant Microsoft in kommenden Preview-Versionen weitere Konstrukte in Extension-Bl\u00f6cken zu erlauben, etwa Konstruktoren. Die Syntax f\u00fcr Extensions, die Microsoft f\u00fcr C# 13.0 in Arbeit hatte (public implicit extension Name for Typ) wurde verworfen.<\/p>\n<p>public class StringExtensionDemo<br \/>\n{<br \/>\n   public void Run()<br \/>\n   {<br \/>\n      string s1old = &#8222;Hello World&#8220;;<br \/>\n      string s1oldtruncated = s1old.TruncateClassic(5);<br \/>\n      Console.WriteLine(s1oldtruncated); \/\/ Hello&#8230;<br \/>\n      string s2old = null;<br \/>\n      Console.WriteLine(s2old.IsEmptyClassic()); \/\/ true<\/p>\n<p>      string s1 = &#8222;Hello World&#8220;;<br \/>\n      string s1truncated = s1.Truncate(5);<br \/>\n      Console.WriteLine(s1truncated); \/\/ Hello&#8230;<\/p>\n<p>      string s2 = null;<br \/>\n      Console.WriteLine(s2.IsEmpty); \/\/ true<\/p>\n<p>      string s3 = string.Create(5, &#8218;#&#8216;);<br \/>\n      Console.WriteLine(s3); \/\/ &#8222;#####&#8220;<br \/>\n   }<br \/>\n}<\/p>\n<p>Listing 3: Aufruf der Erweiterungen in Listing 1 und 2<\/p>\n<p>Null-Conditional Assignment in C# 14.0<\/p>\n<p>Ein weiteres sehr hilfreiches neues Sprachkonstrukt in C# 14.0 nennt Microsoft Null-Conditional Assignment. Damit k\u00f6nnen Entwicklerinnen und Entwickler eine Zuweisung an eine Eigenschaft machen, ohne vorher zu pr\u00fcfen, ob das Objekt null ist. Anstelle von<\/p>\n<p>Website aktuelleDOTNETWebsite = Website.Load(123);<br \/>\nif (aktuelleDOTNETWebsite!= null)<br \/>\n{<br \/>\n \/\/ Aktualisieren der URL<br \/>\n aktuelleDOTNETWebsite.Url = &#8222;https:\/\/www.dotnet10.de&#8220;;<br \/>\n}<\/p>\n<p>darf man nun verk\u00fcrzt mit dem Fragezeichen schreiben:<\/p>\n<p>aktuelleDOTNETWebsite?.Url = &#8222;https:\/\/www.dotnet10.de&#8220;;<\/p>\n<p>Dies f\u00fchrt zur Laufzeit zu keinem Fehler. Allerdings passiert auch rein gar nichts, falls die Variable aktuelleDOTNETWebsite den Wert null besitzt.<\/p>\n<p>Verbesserungen f\u00fcr OpenAPI Specification (OAS)<\/p>\n<p>In der Projektvorlage &#8222;ASP.NET Core Web API (native AOT)&#8220; ist nun die Metadatengenerierung mit OpenAPI Specification (OAS) im Standard aktiviert. Mit dem Befehl<\/p>\n<p>dotnet new webapiaot &#8211;name ITVisionsWebAPI<\/p>\n<p>entsteht ein Projekt, das das NuGet-Paket Microsoft.AspNetCore.OpenApi referenziert und die OpenAPI-Unterst\u00fctzung in Program.cs mit<\/p>\n<p>builder.Services.AddOpenApi();<\/p>\n<p>und<\/p>\n<p>app.MapOpenApi();<\/p>\n<p>aktiviert.<\/p>\n<p>Bisher war die OpenAPI-Unterst\u00fctzung nur in der Projektvorlage &#8222;webapi&#8220; aktiv, die keine Kompilierung mit dem NativeAOT-Compiler erlaubt. In der Projektvorlage &#8222;webapiaot&#8220; k\u00f6nnen Entwicklerinnen und Entwickler die OpenAPI-Features wahlweise auch deaktivieren, mit dem Parameter &#8211;no-openapi:<\/p>\n<p>dotnet new webapiaot &#8211;name ITVisionsWebAPI &#8211;no-openapi<\/p>\n<p>Das in Preview 2 vorhandene Problem, dass WebAPI-Projekte <a href=\"https:\/\/www.heise.de\/news\/NET-10-0-Preview-2-ist-mit-heisser-Nadel-gestrickt-10321126.html\" rel=\"nofollow noopener\" target=\"_blank\">immer einen 404-Fehler lieferten<\/a>, ist in Preview 3 behoben. Die XML-Kommentarinformationen ,  und , die man seit Preview 2 in das OpenAPI-Dokument \u00fcbernehmen kann, sind dort sichtbar in summary und description.<\/p>\n<p>Validierung f\u00fcr ASP.NET Core Minimal WebAPIs<\/p>\n<p>ASP.NET Core Minimal WebAPIs beherrschen nun auch die Parametervalidierung mit Data Annotations. Das konnten <a href=\"https:\/\/learn.microsoft.com\/en-us\/aspnet\/web-api\/overview\/formats-and-model-binding\/model-validation-in-aspnet-web-api\" rel=\"external noopener nofollow\" target=\"_blank\">bisher nur die Controller-basierten WebAPIs<\/a>.<\/p>\n<p>F\u00fcr Minimal WebAPIs m\u00fcssen Entwicklerinnen und Entwickler das Validierungsfeature allerdings erst in der Projektdatei aktivieren<\/p>\n<p>$(InterceptorsNamespaces);Microsoft.AspNetCore.Http.Validation.Generated<\/p>\n<p>ebenso wie in der Startdatei:<\/p>\n<p>builder.Services.AddValidation();<\/p>\n<p>Dann kann man mit den bekannten Validierungsannotationen wie [MinLength], [MaxLength], [Range], [Url], [EmailAddress], [Phone], [CreditCard], [RegularExpression] und vielen mehr (siehe Liste <a href=\"https:\/\/learn.microsoft.com\/de-de\/dotnet\/api\/system.componentmodel.dataannotations\" rel=\"external noopener nofollow\" target=\"_blank\">in Microsoft Learn<\/a>) auch in Minimal WebAPIs arbeiten, zum Beispiel:<\/p>\n<p>app.MapGet(&#8222;\/checkwebsite&#8220;, ([MinLength(5)] string name, [Url] string url)<br \/>\n       =&gt; WebsiteChecker.CheckWebsite(name, url));<\/p>\n<p>Hier f\u00fchrt nun der HTTP-Aufruf<\/p>\n<p>http:\/\/localhost:5245\/checkwebsite?name=ITVisions&#038;url=www.IT-Visions.de<\/p>\n<p>zur Laufzeit zur R\u00fcckgabe eines JSON-Dokuments mit zwei Validierungsfehlern (siehe Abbildung 2).<\/p>\n<p>      <a href=\"https:\/\/www.heise.de\/imgs\/18\/4\/8\/3\/6\/1\/3\/4\/image2-22898726e5a93072.png\" rel=\"nofollow noopener\" target=\"_blank\"><\/p>\n<p>  <img loading=\"lazy\" decoding=\"async\" alt=\"Beide Parameter beim Aufruf dieses ASP.NET Core Minimal WebAPI entsprachen hier nicht den Validierungsregeln (Abb. 2)\" height=\"450\" src=\"data:image\/svg+xml,%3Csvg xmlns='http:\/\/www.w3.org\/2000\/svg' width='696px' height='391px' viewBox='0 0 696 391'%3E%3Crect x='0' y='0' width='696' height='391' fill='%23f2f2f2'%3E%3C\/rect%3E%3C\/svg%3E\" style=\"aspect-ratio: 1077 \/ 450; object-fit: cover;\" width=\"1077\"\/><\/p>\n<p>      <\/a><\/p>\n<p>Beide Parameter beim Aufruf dieses ASP.NET Core Minimal WebAPI entsprachen hier nicht den Validierungsregeln (Abb. 2).<\/p>\n<p class=\"a-caption__source\">\n      (Bild:\u00a0Holger Schwichtenberg)\n    <\/p>\n<p>Deklarativer Persistent Component State in Blazor 10.0<\/p>\n<p>Microsofts Webframework ASP.NET Core erlaubt bei Blazor Server und Blazor WebAssembly bisher schon die \u00dcbergabe von Daten zwischen dem Prerendering und dem Hauptrendering via JSON-Anhang in HTML-Dokumenten. Dieser Persistent Component State war bisher aber recht aufwendig f\u00fcr Entwicklerinnen und Entwickler in der Realisierung, denn man musste zun\u00e4chst ein Objekt per Dependency Injection bekommen<\/p>\n<p>@inject PersistentComponentState ApplicationState<\/p>\n<p>und dann den Zustand als Objekt dort ablegen<\/p>\n<p>private PersistingComponentStateSubscription? persistingSubscription;<\/p>\n<p>persistingSubscription = ApplicationState.RegisterOnPersisting(() =&gt;<br \/>\n        {<br \/>\n            ApplicationState.PersistAsJson(&#8222;name&#8220;, daten);<br \/>\n            return Task.CompletedTask;<br \/>\n        });<\/p>\n<p>und wieder explizit herausholen<\/p>\n<p>if (ApplicationState.TryTakeFromJson(&#8222;name&#8220;, out var daten))<br \/>\n        {<br \/>\n            Daten = daten;<br \/>\n        }<\/p>\n<p>Dies hat Microsoft in .NET 10.0 Preview 3 radikal vereinfacht, mit dem deklarativen Persistent Component State. Entwicklerinnen und Entwickler m\u00fcssen jetzt nur noch eine Property mit der Annotation [SupplyParameterFromPersistentComponentState] versehen und sich sonst um nichts k\u00fcmmern:<\/p>\n<p>[SupplyParameterFromPersistentComponentState]<br \/>\npublic Daten? daten { get; set; }<\/p>\n<p>Verbesserungen f\u00fcr Blazor WebAssembly<\/p>\n<p>Das in Blazor 9.0 eingef\u00fchrte Fingerprinting funktioniert nun auch f\u00fcr die in Blazor eingebaute JavaScript-Datei in den sogenannten &#8222;Standalone Blazor WebAssembly&#8220;-Projekten, die nicht in ASP.NET Core betrieben werden, sondern auf einem statischen Webserver gehostet sein k\u00f6nnen. Dazu verwendet man in den Projekteinstellungen<\/p>\n<p>true<\/p>\n<p>und im HTML-Kopfbereich<\/p>\n<p>Das Script-Tag ist dann<\/p>\n<p>Diese Verbesserung ist in der Projektvorlage aber noch nicht so umgesetzt, was man sieht, wenn man ein neues Projekt anlegt:<\/p>\n<p>dotnet new blazorwasm -n ITVisionsDemo<\/p>\n<p>F\u00fcr Blazor WebAssembly musste man die Umgebungsdefinition (Development, Staging, Production) <a href=\"https:\/\/learn.microsoft.com\/en-us\/aspnet\/core\/blazor\/fundamentals\/environments?view=aspnetcore-9.0#set-the-client-side-environment-via-header\" rel=\"external noopener nofollow\" target=\"_blank\">bisher per HTTP-Header vornehmen<\/a>. Nun nimmt Microsoft beim Kompilieren von Blazor-WebAssembly-Anwendungen automatisch folgende Umgebungen an:<\/p>\n<ul class=\"rte__list rte__list--unordered\">\n<li>Bei dotnet build: &#8222;Development&#8220;<\/li>\n<li>Bei dotnet publish: &#8222;Production&#8220;<\/li>\n<\/ul>\n<p>Entwicklerinnen und Entwickler k\u00f6nnen die Umgebungsart auch per Projekteinstellung explizit setzen, etwa f\u00fcr Staging:<\/p>\n<p>Staging<\/p>\n<p>In Blazor WebAssembly ist in der Klasse HttpClient im Standard nun das Response-Streaming aktiv, um die Leistung zu erh\u00f6hen und den Speicherbedarf zu verringen. Allerdings sind dadurch nur noch asynchrone Operationen m\u00f6glich. Dies geh\u00f6rt zu den Breaking Changes in .NET 10.0, <a href=\"https:\/\/learn.microsoft.com\/en-us\/dotnet\/core\/compatibility\/10.0\" rel=\"external noopener nofollow\" target=\"_blank\">die in Microsoft Learn dokumentiert sind<\/a>. Das Response-Streaming im HttpClient ist deaktivierbar mit:<\/p>\n<p>requestMessage.SetBrowserResponseStreamingEnabled(false);<\/p>\n<p>Verbesserungen in der .NET-Basisklassenbibliothek<\/p>\n<p>Eine Verbesserung f\u00fcr den Zertifikatsexport stand schon <a href=\"https:\/\/github.com\/dotnet\/core\/blob\/main\/release-notes\/10.0\/preview\/preview2\/libraries.md#encryption-algorithm-can-now-be-specified-in-pkcs12pfx-export\" rel=\"external noopener nofollow\" target=\"_blank\">in den Release Notes<\/a> zu .NET 10.0 Preview 2, <a href=\"https:\/\/www.heise.de\/news\/NET-10-0-Preview-2-ist-mit-heisser-Nadel-gestrickt-10321126.html\" rel=\"nofollow noopener\" target=\"_blank\">funktionierte dort aber nicht<\/a>. Nun in Preview 3 kann man tats\u00e4chlich Zertifikate mit AES-Verschl\u00fcsselung und Hashing via SHA-2-256 exportieren, mit der neuen Methode ExportPkcs12() als Erg\u00e4nzung zur bestehenden Methode Export():<\/p>\n<p>byte[] pfxData = cert.ExportPkcs12(Pkcs12ExportPbeParameters.Pbes2Aes256Sha256, password);<\/p>\n<p>Die alten Verfahren (3DES-Versch\u00fcsselung und SHA1-Hashing) aus Export() sind aber auch \u00fcber die neue Methode m\u00f6glich:<\/p>\n<p>byte[] pfxData = cert.ExportPkcs12(Pkcs12ExportPbeParameters.Pkcs12TripleDesSha1, password);<\/p>\n<p>Dar\u00fcber hinaus bietet .NET 10.0 Preview 3 einige kleinere Verbesserungen f\u00fcr Validation Context, Telemetry und ML.NET, <a href=\"https:\/\/github.com\/dotnet\/core\/blob\/main\/release-notes\/10.0\/preview\/preview3\/libraries.md\" rel=\"external noopener nofollow\" target=\"_blank\">die man in den Release Notes findet<\/a>.<\/p>\n<p>Ausblick<\/p>\n<p>Bis zum Erscheinen im November 2025 sind noch vier weitere Preview-Versionen und zwei Release-Candidate-Versionen von .NET 10.0 zu erwarten.<\/p>\n<p>(<a class=\"redakteurskuerzel__link\" href=\"https:\/\/www.heise.de\/news\/mailto:mai@heise.de\" title=\"Maika M\u00f6bus\" rel=\"nofollow noopener\" target=\"_blank\">mai<\/a>)<\/p>\n","protected":false},"excerpt":{"rendered":".NET 10.0 Preview 3 bringt Typ-Erweiterungen .NET 10.0 Preview 3 steht seit gestern zum Download auf der .NET-Downloadseite&hellip;\n","protected":false},"author":2,"featured_media":23850,"comment_status":"","ping_status":"","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[135],"tags":[14235,14236,6541,29,30,196,190,189,445,194,191,193,192],"class_list":{"0":"post-23849","1":"post","2":"type-post","3":"status-publish","4":"format-standard","5":"has-post-thumbnail","7":"category-wissenschaft-technik","8":"tag-net","9":"tag-net-10-0","10":"tag-c","11":"tag-deutschland","12":"tag-germany","13":"tag-it","14":"tag-science","15":"tag-science-technology","16":"tag-softwareentwicklung","17":"tag-technik","18":"tag-technology","19":"tag-wissenschaft","20":"tag-wissenschaft-technik"},"share_on_mastodon":{"url":"https:\/\/pubeurope.com\/@de\/114320332931346283","error":""},"_links":{"self":[{"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/posts\/23849","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/comments?post=23849"}],"version-history":[{"count":0,"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/posts\/23849\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/media\/23850"}],"wp:attachment":[{"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/media?parent=23849"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/categories?post=23849"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.europesays.com\/de\/wp-json\/wp\/v2\/tags?post=23849"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}