Die bessere Idee sind eigentlich Bindings, spricht Du hälst die Daten in einem State und die UI rendert die State.
Was Du machst ist die UI als "Speicher" zu missbrauchen. Das macht sehr viel sehr umständlich.
Du sprichst zwar von der DrawAppointmentsForFreshMonth Methode, Du verwendest sie auch, aber Du hast im Code die Methode nirgends hinterlegt. Da wir keine Glaskugel haben, solltest Du den Inhalt der Methode schon zeigen, sonst machts kein Sinn.
Ob Du Methode aufgerufen wird, kannst Du selbst mit dem Debugger testen.
[Artikel] Debugger: Wie verwende ich den von Visual Studio?
PS: Dein Code ist sehr sehr umständlich und wenn man als Aussenstehender drauf schaut, weiß man nicht wirklich warum Du was tust.
Wenn Du wirklich noch C# 7.3 verwendest; das ist weit über 6 Jahre alt und Du verwendest eine .NET Version, die uralt ist.
[FAQ] Das .NET Ökosystem - .NET, .NET Core, .NET Standard, NuGet und Co
Der erste Abruf der CPU Werte sind immer 0 - und Du erstellst die ganze Zeit den Counter neu. Daher kann auch immer nur 0 heraus kommen.
If the calculated value of a counter depends on two counter reads, the first read operation returns 0.0.
Mit
static void Main(string[] args)
{
PerformanceCounter cpuCounter = new("Processor", "% Processor Time", "_Total");
while (true)
{
Console.WriteLine(cpuCounter.NextValue());
}
}
funktioniert alles einwandfrei.
Dein gesamter Code is aber nich wirklich stabil. Verwende einen PeriodicTimer statt einer Endlosschleife mit einem Thread.Sleep.
zB
static async Task Main(string[] args)
{
CancellationToken token = new(); // optional externes Canceln oder nach Zeit etc.
PerformanceCounter cpuCounter = new("Processor", "% Processor Time", "_Total");
using PeriodicTimer timer = new(TimeSpan.FromSeconds(1));
while (await timer.WaitForNextTickAsync(token) && !token.IsCancellationRequested)
{
Console.WriteLine(cpuCounter.NextValue());
}
}
Zitat von jogibear9988
Muss ich den die Skia und HarfBuzz libs immer mitliefern, oder werden dort auch die auf dem System (wenn vorhanden) existierenden benutzt?
Es gibt kein GAC wie in .NET Framework mehr - Du musst immer alles mitliefern (außer die Runtime, die kann optional mitgeliefert werden). Spielt die Größe eine sehr wichtige Rolle, dann kannst Du evtl Trimming anwenden. Die Build-Zeiten werden dadurch jedoch (irgendwo musses ja her kommen) deutlich erhöht.
Zitat von Palladin007
Das verstehe ich nicht? Angenommen, der ThreadPool würde nicht statisch arbeiten, sondern alle Threads je Instanz verwalten, wo ist dann das Sicherheitsrisiko?
Ich hatte in Erinnerung, dass es einen generellen Security Flaw gibt, wenn eigene Thread Pools abgeleitet werden können aufgrund der Implementierungsart, aber das scheint nur (noch?) für UnsafeQueueUserWorkItem Code Access Security bei zu gelten, siehe Remarks.
Das sieht aus, als würde da etwas fehlen? 😃
Hups. Kommt davon wenn man nebenher aufgefordert wird "mal kurz" was zu machen...
Ich sehe generell beim Drüberschauen keine große Lücke, auf Anhieb.
Zitat von Palladin007
schade, dass der .NET-ThreadPool komplett statisch arbeitet und ich mir keine eigene Instanz bauen kann 😕
Der ThreadPool ist im Endeffekt nichts anderes als eine Implementierung des TaskScheduler auf einer eigenen Ebene. Davon eine eigene Instanz zu erzeugen ist ein potentielles Sicherheitsrisiko. Daher soll der ThreadPool auch nicht verwendet werden, wenn Du sicherheitsrelevante Aufgaben hast und Dein ausführende System keine Zugriffssicherheit des ThreadPools bietet (Du zB das System mit anderen Anwendungen auf der Ebene teilst).
Deine Implementierung SingleThreadTaskScheduler ist also quasi ein Custom Thread Pool. Ich sehe
Kurze Frage zur Problemstellung:
Sind die Aufgaben in den Tasks, auf die Du wartest, identisch?
Also Fragen mehrere Requests zB an was "1+1" ist und Du hast dann ein externen Call, der die "2" liefert?
Kannst Du dann nicht die Anfrage zusammen mit dem Task in einem Dict halten, sodass gar kein zweiter Task erzeugt wird, der nochmal "1+1" beinhaltet, sondern Du hast ja dann den Task schon auf den Du wartest?
e.g. dict.Add("1+1", myTask);
Dann hättest Du die Race-Condition weg-optimiert.
HolidayClient ist in Nager.Date unbekannt; existiert nicht. Erkennt man wenn man einfach die Repository-Suche verwendet.
Kann das sein, dass Du https://github.com/nager/Nager.Holiday meinst? Zumindest spuckt das Google aus wenn man nach nager holidayclient sucht.
Das is ein anderes Projekt, ein anderes Paket und ein anderer Namespace.
Aber habe ich damit nicht immer noch das Problem, dass ein Deadlock auftreten kann, wenn alle ThreadPool-Threads die Ausführung je eines Tasks mit UnsafeQueueUserWorkItem in die ThreadPool-Queue legen, die aber nie ausgeführt werden, weil alle ThreadPool-Threads darauf warten?
Ja, aber das ist ja ein grundlegendes Problem des Henne-Ei Prinzips.
Aber mit
Der betreffende Code kann sehr oft gleichzeitig laufen, also z.B. sehr viele Nutzer, die ein bestimmtes Datum abwarten und dann alle auf einmal los rennen, Requests produzieren und ThreadPool-Threads füllen. Die Requests laufen auch recht lange, es kann also durchaus sein
gehst Du ja bewusst dieses Risiko ein. Daher skaliert man ja zB Ticket-Sale-Systeme auch nicht über diese Art und Weise. Das ist im Endeffekt ja nichts anderes als ein DoS gegen sich selbst.
Der Standard-ThreadPool bei WIn32 hat 1023 Worker und 1000 für async I/O. Musst halt das Erstellen limitieren / extern skalieren. Aber das wäre auch ohne den Pool der Fall, sprich bei manuellem Handling.
Der ThreadPool is nen sehr komplexes und schlaues Konstrukt; vielleicht kann er das ein oder andere auch erkennen. Aber für Long-Running IO ist eigentlich der ThreadPool das falsche Mittel bzw. ist das eigentlich nicht seine beste Stärke. In Deinem Fall is eventuell doch eigenes Management statt Pool der bessere Weg.
Ich hab nen bisschen rum probiert, aber keine funktionierende Lösung in meinem Zeitblock gefunden.
Aber eigentlich bin ich der Meinung, dass das mit Thread.QueueUserWorkItem bzw. Thread.UnsafeQueueUserWorkItem funktionieren müsste.
.GetAwaiter().GetResult() ist Wait() auf reines await-Replacement prinzipiell vorzuziehen, weil zB potentielle Exceptions innerhalb eines Wait() ansonsten zu einem Deadlock führen kann.
Jedoch kann .GetAwaiter().GetResult() in ganz gewissen Szenarien immer noch zu Deadlocks führen. Umgekehrt ausgedrückt gibt es nur ganz arg wenige Szenarien, die überhaupt Deadlock-frei auf Tasks "warten" können.
Nur der Vollständigkeit halber: hab aktuell keine vollständige Lösung auf Deine Frage.
Zitat von Joe78
Bekomme zwar ein Bild auch über ShellExecuteEx geöffnet, aber der Windows Bildbetrachter lässt mich mit den Pfeiltasten auch hier nicht weiter navigieren.
Das is nen bekannter Bug in der App, leider seit Jahren. Der is besonders zu merken, wenn man durch nen OneDrive Ordner navigiert, und die Bilder dynamisch nachgeladen werden. Man muss dann nicht immer, aber oft die App neu starten, ansonsten erkennt werden die neuen/nachgeladenen Bilder nicht erkannt.
Wird wohl nie gefixt werden.
Was soll das denn am Ende werden, oder vereinfachen? Und welche UI Technologie ist das? Forms?
In quasi allen modernen UIs würde man Bindings verwenden - da braucht man das alles nicht.
Wenn ich mir grob denken kann, dass es hier um Lokalisierung geht wäre ich überrascht, dass Du die Anforderungen hast, dass Du was völlig Neues erfinden müsstest.
Wenn Du nur den Source haben willst, dann nimm einfach den HttpClient; da sind auch dutzende Beispiele in den MS Docs.
WebView2 is wenn Du einen Browser nachahmen willst, zB wegen JavaScript, (Pre-)Rendering oder die UI dazu anzeigen willst (zB in WPF) etc..
Vermutlich brauchst Du zweiteres, weil Du mit dem DOM arbeitest in Deinem Code.
In beiden Fällen musst Du "einfach" async await korrekt anwenden, wie in meinem Beispiel.
string html = await InternetAsync(LStr_Link, WvLinkInhalt);
async await ist wirklich was, was Du verstehen musst. Lern es. Inverstier 20 Stunden. Du brauchst es jeden Tag. Da reicht es nicht einfach den Code zu kopieren.
Das ist wirklich mittlerweile ein Basiswissen in C#, das man wirklich leider nicht mit Copy Paste lernen kann.
Und wenn Du etwas "nicht hin kriegst", was kriegst Du nicht hin? Erklär es konkret, dann kann man auch konkret antworten. Aber mein Ziel ist es, dass Du es verstehst und dann werde ich nicht Dein Code Generator sein. Da hast nix gelernt und Dir is nich geholfen.
Es gibt keine Garantie, dass Drittanwendungen sich so verhalten, wie Du Dir das wünscht.
bei z.B. Bilder aus Chrome oder Edge bekomme ich nur FileNames und MemoryStream gibt null aus.
Verwendet man Drag and Drop mit Chromium-basierten Browsern (zB das Bild einer Webseite), dann wird standardmäßig die URL in der aktuellen Outlook-Version rein kopiert und nicht die Datei selbst.
In alten Versionen wird das Drag- and Drop fast vollständig blockiert.
Task<string> task = InternetAsync(LStr_Link, WvLinkInhalt);
String html = task.ToString();
Das kann Dir niemals den HTML Code liefern, weil Du das ToString auf die Task Instanz und nicht auf die Rückgabe von InternetAsync anwendest.
Hier fehlt einfach das await.
string html = await InternetAsync(LStr_Link, WvLinkInhalt);
Auch der aufrufende Code muß
await
benutzen - ansonsten wird der ganze Code synchron ausgewertet.
In dem Fall ist es Parallel bzw. Fire and Forget.
Mit dem Task wird nichts mehr gemacht; der läuft einfach im "Hintergrund" und das Resultat wird "verworfen".
Im Endeffekt ist das parallel.
Geht nicht nur um den Store; ohne Zertifikat erhalten alle Deine Anwender immer eine Warnung - oder wird vollständig blockiert - vom Smart Screen, auch wenn sie Deine Exe von Deiner Seite laden. So funktioniert nun mal Software Verteilung auf Geräten. Geht Dir nicht anders unter Android, iOS...
Am Ende ist das nachher Reputation alá "Person/Firma XYZ verteilt Software, die Warnungen auf PCs auslösen"
die dann wie die Nadel im Heuhaufen irgendwo im Internet steht
Get started: Publish your first app in the Microsoft Store ist der erste Treffer bei der Google Suche nach how to deploy app to windows store 😃
The binary and all of its Portable Executable (PE) files must be digitally signed with a code signing certificate that chains up to a certificate issued by a Certificate Authority (CA) that is part of the Microsoft Trusted Root Program.
Microsoft Store Policies, die überall in der Store Doc verlinkt sind.
Dein Self Signed Cert ist in diesem Fall völlig wertlos.
Das ist als ob Du Dir selbst nen Personalausweis am Küchentisch malst und drauf schreibst Du bist der Helmut. Nen echter Perso kommt halt von einer vertrauenswürdigen Stelle (Rathaus), hat Sicherheitsmerkmale und eine Gültigkeit - und wird daher anerkannt.
Nichts anderes ist hier ein Zertifikat. Das wird von vertrauenswürdigen Stellen ausgegeben, hat Sicherheitsmerkmale (Chain of Trust) und hat eine Gültigkeit.
Dein Self Cert ist nur für Dich gültig, wie Dein selbst gemalter Perso, sonst für niemand. Du wirst da nie eine Antwort erhalten.
Ein Code Signing Cert ist dazu da, dass die Chain of Trust eingehalten wird, und Deine Identität festgestellt wird - falls damit schindluder betrieben wird.
Die Chain of Trust ist auch das, dass Dein Cert auf Windows und Co überall, nicht nur bei Dir lokal, eine Gültigkeit hat.
Self Signed Certs haben durchaus ihre berechtigte Existenz und hat völlig valide Anwendungsfälle - genauso selbst erzeugte Root CAs - aber leider nicht wenn man Software an Dritte verteilen will.
Willst Du Software verteilen, egal ob via Store oder als Download, musst Du Dich an gewisse Regeln halten. Diese sind dazu da, dass das Ökosystem an Software einigermaßen seriös bleibt und Anwender geschützt werden.
Eine dieser Regeln ist, dass Du Software immer signieren musst - ansonsten bekommst den Smart Screen.
Gleiches Thema vor ein paar Tagen: SETUP.exe von meiner Homepage wird blockiert
Da sind entsprechend Links und Erklärungen enthalten, zB Sign a Windows 10 app package
Hinzu kommen Regeln für Stores (egal ob Windows, Apple, Android und Co) - und auch hier muss sowohl die Sofware wie auch das Paket selbst eindeutig valdie signiert werden (+ weitere Prüfungen).
Der Windows Store ist sehr gut dokumentiert. Dort sind auch alle Regeln und Anforderungen gelistet, um Apps anbieten zu dürfen. Und der Windows Store ist sogar noch einigermaßen einfach zu bedienen / Software damit zu verteilen.
Get started: Publish your first app in the Microsoft Store
Die Zielgruppe sind aber halt schon Entwickler, die ein paar Grundlagen kennen. Und wenn man die Grundlagen kennt, dann ist das auch alles nicht mehr kompliziert und schränkt auch niemanden in der Kreativität ein. Der Sinn ist es nämlich nicht, den Store mit unnützen, "unseriösen" Apps zu fluten - daher gibts Anforderungen an die Sicherheit für Anwender.
Gar nicht, weil so Konsolen nicht funktionieren; weder auf Windows noch auf anderen Betriebssystemen. Eine Konsole ist nur eine Visualisierung eines Datenstreams. Es ist keine Benutzeroberfläche mit Eingabelimits o.ä.
Im Endeffekt musst Du jede Eingabe annehmen, dann validieren und wenns nich passt das letzte Zeichen in der Console löschen (überschreiben).
Es gibt fertige .NET Libs, die sowas prinzipiell können bzw. einfachere Möglichkeiten haben, als das selbst umzusetzen. Sowas nennt sich dann Interactive Shell.
Zitat von GeneVorph
Ich tendiere langsam Richtung Bug:
In .NET? Die Wahrscheinlichkeit ist nahezu 0.
Deine verwendeten Technologien sind so dermaßen weit verbreitet, etabliert und stabil, dass quasi jeder Bug bekannt ist - wenn überhaupt hier einer existiert.
Dein Code hat aber mit Sicherheit Bugs, allein das ganze Region-Handling strikt auf Komma etc... auch das ganze StringBuilder-Handling macht so kein wirklichen sinn.
Wo genau nun Dein inhaltlicher Bug ist, sehe ich auch nicht; aber die Wahrscheinlichkeit, dass es an .NET/WPF liegt, ist echt gering.
Aktuelle Projekte, an denen noch aktiv gearbeitet wird, komplett auf NSubsitute umgezogen, sowohl eigene wie auch Company-/Kunden-Projekte.
Gilt auch für alle weiteren Libs des Autors - das Vertrauen ist da einfach komplett gebrochen und die Gefahr viel zu groß.
Hab sehr viel mit Copilot oder ChatGPT/Azure OpenAI an der Stelle automatisiert; ging selbst mit großen Solutions sehr fix.
Aber, mir persönlich gefällt es nicht in einigen Projekten Moq zu verwenden und in anderen Nsubstitute. Und jetzt die älteren Projekte auch auf Nsubstitut zu migrieren → da gibt es wichtigeres zu tun.
Wir haben bei jeglichen Testanpassungen die Regel, dass Moq rausgeworfen wird.
Teilweise wurde also in einem Rutsch migriert, teilweise nach und nach.
Typischer Fall, wenn so ein Fehler auftaucht ist, dass Du das NuGet falsch in Dein Projekt gesetzt hast.
Hast Du direkt eine Assembly referenziert, oder wirklich das NuGet Paket "installiert", in Deiner csproj?
Es wird sich wegen Microsoft.Extension.DependenyInjection.Abstraction beschwert, aber Du nennst Microsoft.Extension.DependenyInjection.
Der Verweis auf Microsoft.Extension.DependenyInjection ist hier korrekt, das Abstraction ist eine sub-dependency (und notwendig).
Daher weitere Möglichkeiten:
Zum Thema:
Ich weiß nicht, was Dein Ziel ist, aber DI ist eigentlich nicht dafür da, so Instanzen von (in Deinem Fall) Charaktere zu erstellen. Zumindest wäre das sehr sehr unüblich. Fühlt sich für mich nach zu viel des Guten an - etwas over engineered.
Das DI dürfte auch nicht funktionieren, weil dem DI Provider die Info fehlt, wie ein Charakter erstellt wird. Du hast einen Konstruktor, der Parameter erwartet - die kennt aber das DI nicht.
Ein üblicherer Fall wäre, dass Du eine Factory erstellst, die einen Charakter erzeugt, und die Factory ist über DI zugreifbar. Die Idee von DI ist schließlich zB Implementierungen zu tauschen und Abhängigkeiten zu lösen.
IServiceCollection services = new ServiceCollection();
services.AddTransient<ICharacterFactory, CharacterFactory>();
IServiceProvider provider = services.BuildServiceProvider();
ICharacterFactory factory = provider.GetRequiredService<ICharacterFactory >();
ICharacter newChar = factory.Create("Sotti", 0); // liefert zB das ICharacter als Character-Class
Damit ist Dein Code von der Implementierung der Factory getrennt; Du kannst jederzeit damit eine andere Factory registrieren, ohne Deinen Code ändern zu müssen.
services.AddTransient<ICharacterFactory, CharacterFactoryDieNochVielBesserIst>();
ICharacter newChar = factory.Create("Sotti", 0); // liefert zB das ICharacter dann als zB BetterCharacter-Class
Das ganze nennt sich Factory Pattern: https://refactoring.guru/design-patterns/factory-method/csharp/example
Stichworte wie TDD, "Clean Code" [...] dienen (längerfristig) dem Menschen um Änderungen oder Erweiterungen an der Codebasis nur an einer (zentralen) Stelle vornehmen zu müssen.
Würde ich bei diesen beiden Punkten so niemals unterschreiben; ganz im Gegenteil.
Ja, man sollte als professioneller Entwickler wissen, was TDD ist - nicht umsonst stellt sich immer mehr die Frage, ob TDD wirklich noch relevant ist. "Clean Code" ist ein 20 Jahre altes Konzept, das teilweise auf Ideen und Lösungen basiert, als es noch weniger Tooling gab. Da sind sicherlich Aspekte dabei, die weiterhin ihre Gültigkeit haben - aber vor allem die deutschsprachige "Clean Code Developer"-Bewegung ist (in meinen Augen) eher eine Religion, als eine wirkliche Hilfe.
Ich meide bewusst auch gewisse Clean Code-Diskissionen auf deutschen Konferenzen, wenn gewisse Personen dabei sind, denen es ganz ganz offensichtlich nur um die eigene Agenda und Religion geht. Gibt aber teilweise auch gutes Hinterfragen, wie zB "ist Clean Code in Zeiten von AI generiertem Code noch relevant" (Open Space Karlsruhe, 2024).
Ja, man sollte wissen, was all diese Dinge sind - das ist keine Garantie, dass Software "besser wird". Und alles sowieso keine Themen für Einsteiger.
Beispiel ist im Link, den ich Dir gegeben hab. Hab auch nen Privatleben und nich wirklich Zeit für jeden seinen Code zu schreiben 😉
Wenn es Dir um das generelle Handling geht (inkl später MVVM): man würde das gar nicht so machen, weil das wahnsinnig ineffizient und langsam ist - und mit größeren Datenmengen auch gar nicht funktioniert.
"Richtig" würde man es machen, dass man Daten über einen DAL lädt (Entitäten via Repositories). Daten werden dann an die UI gebunden und Änderungen führen dazu, dass ein Command den/die Datenbankeinträge über den DAL aktualisiert.
In größeren Anwendungen hätte man dann zusätzlich noch ein State Management, zB via Reactive Extensions.
DataTables und irgendwelcher Adapter verwendet man wenn überhaupt nur noch in Mini-Tools.
Du solltest Dir für die Serialisierung von Daten immer eine eigene Klasse (Complex Object) bauen, die Deine Serialisierung (also XML, Json, etc..) repräsentiert. Aktuell schmeisst Du nur eine Liste rein und sagst dem Serializer "mach einfach mal". Daher kommt als Root auch sowas raus wie ArrayOfDataSource
So ein Vorgehen hat den enormen Nachteil, dass Deine Stuktur völlig anders sein kann, wenn Du den Serializer austauschst.
.NET Doc: Examples of XML Serialization
Ich würde aber gerne dass die BuildVersion eine eigene Bezeichnung hat und nicht die Data-Source.
Deine XML ist genau das, was Du da als Objekt myObject
etc darstellst.
Soll Deine XML anders aussehen, dann brauchst Du dafür extra Objekte oder Du serialisierst die XML manuell (quasi Nodes von Hand definieren).
Es ist ohnehin empfohlen, dass Deine XML Struktur als eigene Objekte definiert werden, sodass sich die Struktur der Dateien nicht ändert, wenn sich Deine UI/Logik-Objekte ändern. Sowas nennt man im Allgemeinen Data Transfer Objects.
Ja, das bedeutet, dass Du manches doppelt hast und von Hand das Mapping machen musst; aber im Endeffekt ist genau das Versionierung.
Willst Du eine Multi-Versionierung Deiner XML Dateien, dann kannst Du ohnehin in den meisten Fällen nicht über diese Wege serialisieren.
Dann musst Du erstmal die Version-Node manuell laden und dann den richtigen Serializer/Parser zur richtigen Version verwenden - was dann in der Folge auch heisst, dass Du mehrere XML-Objekte brauchst um die verschiedenen Versionen darstellen zu können.
Ok, und warum schaust Du dann nicht einfach in die Docs? Die Connection Strings von Sqlite sind standardisiert.
.NET Sqlite Connection Strings oder direkt die native Doc https://www.sqlite.org/docs.html
Wie das ganze richtig funktioniert, keine Ahnung. Ich finde da auch keine Schritt für Schritt Anleitung.
Naja, das ist halt ein Management Tool. Die Grundlagen davon werden da natürlich nicht abgedeckt.
Google Suche nach .NET Sqlite Tutorial hat ja tausende von Treffern, sowohl Blog, Docs und Videos.
Als Feedback: les mal Deinen eigenen Beitrag durch.
Glaubst Du jemand ohne den Blick vor Deinen Monitor versteht, was Du vor Dir hast und was Dein Problem ist?
Ich kann mir, weil ichs kenn, nun Anhand vom ErikEJ Kürzel im Screenshot herleiten, dass Du die EF Core Power Tools meinst. Aber der Rest... keine Ahnung wovon Du sprichst.
Aber wenn ich die ConnectionString meine test.db eintrage. kommt diese Fehlermeldung, siehe Bild 02.png
Wir haben leider keine Glaskugel. Welchen ConnectionString nutzt Du denn und woher kommt der Error-Screenshot?
Wie kann ich Acrobat "automatisieren". Ich würde ja eigentlich nur "Öffnen", "Speichern unter..." und "Schließen" benötigen.
Jedes UI Control hat nen eigenes Handle; das Window, nen Button... musst Dir also die Handles besorgen und dann die Handles steuern. Und ja, dafür gibts keine fertige Anleitung.
Mit FindWindowExA kannst Dir das erste Handle holen; und dann musst durch die Child Handles iterieren.
Aber Du kannst Dir anschauen, wie andere das machen: https://www.google.com/search?q=.net+windows+window+handles
Kann jedoch jederzeit sein, dass Du das mit jeder Acrobat-Aktualisierung anpassen musst.
Wichtig wäre dabei auch, dass die Ausgabedatei die gleiche Struktur hat, die ACROBAT erzeugt.
Das ist quasi ausgeschlossen - oder reiner Zufall; ausser, wenn Du die Anwendung Acrobat selbst automatisierst oder eben die kostenpflichtige PDF Service API von Adobe verwendest.
PDF ist kein offenes Dateiformat und quasi jede andere Implementierung basiert auf Reverse Engineering und damit ggfls. unterschiedlichen Ergebnissen. Und weil es ein geschlossenes aber leider sehr beliebtes Dateiformat ist, sind kostenfreie / offene Bibliotheken für den kommerziellen Zweck in allen Programmiersprachen Mangelware (beachte auch dazu die Lizenz von iText 7).
Willst Du qualitativ gutes PDF Handling, dann wirst Du leider - das zeigt die Erfahrung - um kostenpflichtige Bibliotheken nicht drum herum kommen.
Ein Repository kümmert sich um die Entität, die Du im Set definierst. Nicht mehr, nicht weniger.
Wenn Dein Join auf dieser Entity basiert bzw. den Start hat, darf das Teil des Repositories sein; das nennt man dann einfach Projektion.
Um Projektionen einfacher zu definieren, kann man sich mit LinqKit Profiles definieren.
https://github.com/BenjaminAbt/efcore-best-practises/blob/main/src/EntityFrameworkDemo/Database/Projections/Profiles/MyEntityNameProjectionProfiles.cs
Im Repository muss man dann nur noch Queries definieren; Queries sind Abfragen ohne Materialisierung - geben als IQueryable zurück.
public IQueryable<MyEntity> QueryById(MyEntityId id, DbTrackingOptions to)
=> Query(to).Where(MyEntityQuery.WithId(id)); // query by Id using our static Expressions
// because the underlaying Query is using AsExpandable, we dont have to put that onto every query method
Also es kann sich schon das eine oder andere ändern.
Das ist die ganz normale Schutzklausel - wie quasi überall - sodass Microsoft dauerhaft die Inhalte des Action Pakets, was ja eine Subscription ist, ändern darf. Im Endeffekt passiert das ja bei (fast) jedem Renewal der Partner Benefits. Eine Dokumentation ist halt kein fester Bestandteil einer Bestellung; d.h. die Inhalte können sich zum Bestellzeitpunkt eben ändern.
Ewig leidiges Thema und einzig offizielle Kommunikation ist:
WebAssembly bzw. Blazor ist nur die dynamische Runtime. Deine Oberfläche bleibt HTML und Du musst auf HTML Features zurück greifen.
Technisch gesehen würde hier Blazor mit der HTML Canvas API oder eben WebGL arbeiten müssen.
Erster Google Treffer: https://github.com/BlazorExtensions/Canvas
Sowas passiert auch, wenn man ein falsches Template oder die falsche Runtime ausgewählt hat.
Was Du willst nennt sich Top Level Statements.
Wundert mich jetzt nicht unbedingt, wenn Du einen fast 15 Jahre alten Link als Referenz nimmst und dann sagst es geht nicht. 2009 hatten wir noch .NET 3 oder .NET 3.5 - also weit bevor es ASP.NET Core in 2015 gab, geschweige denn Kestrel bzw. in der heutigen Form seit 2021.
Mach doch mal das ASP.NET Core Tutorial durch, wenn Du selbst sagst Du hast damit noch nie gearbeitet?
Die Doc is ausführlich und sehr groß - und das ist gut so.
Deine Fragen dürften in den ersten Einsteigerkapiteln beantwortet werden plus nen paar Google-Suchen wie kestrel https certificate
Kestrel - Configure HTTPS
Der Windows Store ist noch strenger. Das Signieren entfällt nicht, sondern ist eine absolute Pflicht.
App package signing is a required step in the process of creating a Windows 10 app package that can be deployed. Windows 10 requires all applications to be signed with a valid code signing certificate.
Du wirst die notwendigen Interop-Assemblies nicht installiert haben. Siehe Hinweis von Th69.
Musst bei der Visual Studio Installation das "Office Development" mit aktivieren; geht auch nachträglich über den Visual Studio Installer.
Bezogen auf Deine Signatur: man muss halt auch die Antwort lesen, wenn man jemand fragt, der es weiß.
Weil Du schreibst, dass Du schon länger nicht mehr mit Office zutun hattest: Interop Schnittstellen sind seit über 10 Jahre abgekündigt und die einzig aktuelle Client-API ist die JavaScript-API. Einige Client-APIs haben sich auch in die Office 365 HTTP APIs (Serverseitig) verlagert. Gewisse Automatismen muss man also gegen deren HTTP API Endpunkt ausführen, nicht mehr gegen den Client.
Die neuen Office-Versionen lassen sich bereits mit Interop nicht mehr automatisieren.
Wenn Du Dokumente automatisieren willst, dann verwende das OpenXML SDK.
Das sind keine speziellen .NET Zertifikate, sondern Code Signing Certificates. Und ja - günstig sind diese nicht.
In Azure gibts das ganze mittlerweile als (relativ preiswerten) Service in der Preview: https://learn.microsoft.com/en-us/azure/trusted-signing/
Sind aber immer noch ~100€ im Jahr.
Hinter solch einem Certificate steckt im Endeffekt eine Firma mit Reputation. Und ja, leider ist es so: je teurer desto vertrauenswürdiger.
Anbieter sind GlobalSign, DigiCert, Sectigo, ...
Ich mach aber keinerlei Desktop-Software, daher kann ich Dir keine aktuelle Erfahrung geben, welches Cert "das beste" Gesamtpaket für Dich ist / sein könnte.
ASP.net ist wenn ich es richtig sehe keine API sondern ein Services ähnlich wie PHP. Es ist schon ein kompletten Server mit Infrastruktur.
ASP mit PHP zu vergleichen is schon spannend.
Nein, das ist nicht im Ansatz richtig. PHP kann ungefähr 10% von dem, was ASP.NET kann und wofür es gedacht ist.
Griffen hingegen ist nur das https Protokoll. Ich übernehme die Infrastruktur. Sowas suche ich.
Gut, das jetz als "API für HTTP" zu beschreiben is durchaus interessant - aber ja, dafür gibts zB Kestrel.
Ja, Kestrel kennt Dependencies von ASP.NET Core - kann aber ohne ASP.NET Core betrieben werden - vice versa.
Quasi alle neue Runtime-Frameworks von Microsoft basieren auf Kestrel (ASP.NET Core, YARP...) wie auch mehrere Azure Services.
Das was ich dann auch noch sehe ich muss das ASP Framework mitliefern für die Installation.
Nein, so funktioniert modernes .NET nicht. Sowas wird ohnehin nicht installiert, sondern ist Teil Deiner Bits. Sowas nennt sich Self Contained.
Warum Du den gezeigten Code mit Modulen etc umsetzt... versteh ich nicht.
Sowas kann man binnen weniger Zeilen mit ASP.NET Core direkt einfach, stabil, simpel machen und braucht nicht irgendwelchen (toten?) Libs.
Was is denn eigentlich Deine Frage? Soll Dir jemand eine Alternative zu Griffin suchen, oder wie?
Fürchte, dass Dein aktuellen Server quasi niemand kennt - da wirst Dich selbst auf die Suche nach Alternativen machen müssen. Das Ding ist mit 90k totalen Downloads in 6 Jahren de facto unbekannt.
Wie können (und werden) Dir, selbst wenn wir wöllten, die Evaluierung ja auch nicht abnehmen können. Das ist Deine Verantwortung als Entwickler.
Ich bräuchte bitte mehr Informationen.
Das is ja was, was Du selbst machen kannst. Die Idee des Forums ist ja nicht, für Dich aus der Doku zu kopieren. Das kannst ja irgendwie selbst durchlesen, wa?
Eine Exe ist kein Problem. Das Problem wird vor allem sein, dass Deine Exe keinerlei digitale Signatur hat - und das mag Windows gar nicht.
Ohne Signatur wirst Du auf den aller meisten Systemen - und das ist gut so - eine Warnung erhalten.
"FIMANSolar.exe wird häufig nicht heruntergeladen. Stellen Sie sicher, dass Sie FIMANSolar.exe vertrauen, bevor Sie es öffnen."
Hier war vor nem Monat das gleiche Thema dazu, siehe meine Antworten dort.
Windows Smartcreen Warnung bei Software-Download
Hier, nen Bild das fast 10 Jahre alt ist - zeigt sehr vereinfacht , wie Tasks funktionieren. Hab nur noch das Bild mit Wasserzeichen, leider nicht mehr ohne.
https://cdn.mycsharp.de/forumpostattachments/attachment-13292.png
Ich nehme mal an, dass Du zu diesem Fazit kommst, weil Du halt nicht weißt was Tasks sind und wie diese im Zusammenspiel mit Threads wirken.
Anders kann ich das Fazit "ein Task sei besser als mehrere" nicht interpretieren. Deine Lösung hat einfach eklatante Fehler, wie Thread.Sleep. Das untergräbt das gesamte Task-Konzept.
Klar, am Ende entscheidest Du, wie Du es umsetzen willst. Wenn das am Ende die Kopf-durch-die-Wand-Variante ist, dann ist das eben so.
Du kannst Dich auch einfach mit der Materie mal 2-3h beschäftigen, statt rum zu probieren. async/await und Tasks sind leider Konzeptthemen; daher nicht durch Try-and-Error verstehbar.
Ganz sicher nicht fehl am Platz, weil genau dieses Attribut in der csproj dazu da ist.
Dass eine License-Datei zusätzlich ins Repo gehört: ja.
Ein Paradebeispiel, was man eigentlich genau nicht tun soll.
Thread.Sleep wurde Dir zB schon mal erklärt, wieso das keine gute Idee ist. Steht weiter oben.
Absoluter Pitfall bei async/await.
Dein Vorgehen ist auch nicht die beste Idee. Willst Du wirklich 80.000 Einträge in Deiner UI haben? Wer soll das lesen?
Das kostet Zeit, Arbeitsspeicher - und der Nutzen ist nur semi. Dafür sind Standard UI Komponenten auch gar nicht ausgelegt; die ballern Dir den RAM voll.
Ja, der ExecuteReader ist langsam bei sehr vielen Datenmengen, denn auch er ist nicht darauf ausgelegt.
Du wirst einfach in dem Timeout laufen, weil das eben für den ExecuteReader so lange braucht.
Fazit: lade nicht so viel in eine UI, das ist weder sinnvoll noch jemals schnell - oder eben Timeout erhöhen.
Zitat von AmpelB
Wie würde denn ein "normaler Poller" (das brauche ich ja erst einmal) mit async/await aussehen?
Erste Frage: wieso ein Poller? Technisches Requirement? Normalerweise versucht man Poller zu vermeiden - kostet unnötig Ressourcen.
Wenn Du wirklich einen Poller brauchst, dann gibst dafür den PeriodicTimer.
Am Blogpost Run and manage periodic background tasks in ASP.NET Core 6 with C# hab ich mitgeschrieben und zeigt den Einsatz in ASP.NET Core - kann aber überall identisch verwendet werden. Das Forum führt ebenfalls gewisse Aufgaben Nachts via PeriodicTimer aus.
PS: Asynchrone Programmierung mit C# von Thomas Claudius Huber ist auch 9 Jahre später gerade für Einsteiger immernoch eine gute Quelle, um async/await besser zu verstehen.
Du arbeitest mit Tasks und hier gibt es keine Garantie, dass Dein Task immer im gleichen Thread bleibt. Der Task Scheduler übernimmt den Start, und auch das Management. Der Task kann jederzeit in einen anderen Thread verschoben werden.
Du musst selbst immer, absolut immer sicher stellen, dass Du Dich im Main Thread befindest, wenn Du auf die UI zugreifst.
Es gibt in modernem C# Code eigentlich keinen Grund mehr für die Nutzung des BackgroundWorkers.
async/await und Co sind Konzepte, die den BackgroundWorker vollständig ersetzt haben. Er existiert nur noch aus Kompatibilitätsgründen - und das schon länger als geplant, denn er wurde mal mit .NET 4.5 als Obsolete markiert.