Delphi-PRAXiS
Seite 2 von 2     12   

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Delphi "Single-User" -> "Multi-User" + SQLite (https://www.delphipraxis.net/199807-single-user-multi-user-sqlite.html)

wjjw 22. Feb 2019 13:59

AW: "Single-User" -> "Multi-User" + SQLite
 
Die Kommunikation mit den Clients läuft ja schon perfekt (via Webserver Multi-Thread).
Nun muss ich nur doch die Threads „richtig“ abarbeiten. Speziell DB Operationen. Dazu dachte ich mur das es da vielleicht ein Framework oder Best Practice gibt.
Diser Post sollte dem Zweck dienen.
Also: die Threads synchronisieren / Queuing, ...
Das Hauptprogramm selbst hat einen Thread und der Webserver bekommt von den Clients auch die Nachrichten. Jetzt möchte ich beide so verbinden, das keiner zu lange warten muss bzw. blockiert wird, was als eine nicht verarbeitete Übertragung bedeuten würde.

mkinzler 22. Feb 2019 14:11

AW: "Single-User" -> "Multi-User" + SQLite
 
Warum nicht per REST?
Zitat:

Dazu dachte ich mur das es da vielleicht ein Framework oder Best Practice gibt.
REST. da gibt es im Delphi-Umfeld Lösungen wie DataSnap, Mars, DelphiMVC, DataWare, ...

MichaelT 22. Feb 2019 15:47

AW: "Single-User" -> "Multi-User" + SQLite
 
Das ehrt deine Programmierkünste hilft aber Ende nicht allzuviel.

Läuft in dem Thread der Anwendung der Webserver?

Du bist in der Situation aus Sicht der Anwendung dass du viele Formulare offen hast auf denen ein Timer sitzt der per Zufallszahl einen ButtonClick resp. eine andere Ereignisbehandlung auslöst. Da hilft es auch nicht viel wenn du den 'Webserver' in der Anwendung laufen hast, denn du musst dauern den GUI Thread unterbrechen.

Eigentlich wäre deine Applikation am PC eine Anwendung die vom 'Server' gestartet wurde und nicht umgekehrt.

Du kannst einen Thread machen der eine DB Operation nach der anderen durchführt. Es macht auf jeden Fall Sinn den Empfang der Nachrichten von der Verbuchung zu entkoppeln. Schreibe die empfangene Nachricht in eine File und verbuche sie im Hintergrund.

Sobald du mit Messages und Queuing arbeitest sagst du zurecht der Anwendung ist egal was mit den Daten passiert, sie übergibt nur an den der die Daten weiterschickt und der weiß schon wohin.

Critical Section bieten sich. Ich würde aber nicht soweit gehen, dass ich unter der Kontrolle einer Anwendung mehre Nachrichten empfangende Threads mache die dann mit einem Pool von DB Writer und DB Reader Prozessen kommunizieren.

Da hast du bspw. in PHP denn in dem Fall synchronisiert der Runtime die DB Sessions.

Ich persönlich würde diese Verarbeitung hinter einen isoliert laufenden Webserver stecken. Damit hat du zumindest den Empfang vom Verbuchen entkoppelt.

Critical Sections bieten sich zur Synchronisation an.


Zitat:

Zitat von wjjw (Beitrag 1426257)
Die Kommunikation mit den Clients läuft ja schon perfekt (via Webserver Multi-Thread).


Ghostwalker 23. Feb 2019 04:46

AW: "Single-User" -> "Multi-User" + SQLite
 
Ich persönlich würde die Kommunikation und das DB Handling in ein eigenes Serverprogramm ohne GUI (Dienst/Daemon) auslagern. Das Serverprogramm nimmt die Daten der Clients entgegen, packt diese in eine Que. Ein eigener Thread des Serverprogramm arbeitet die Que ab und trägt diese in die DB ein.

Vorteile:

- Keine Synchronisatzion mit einer GUI
- Keine Blockade der Clients
- Wenns zuviel wird, kann man das ganze auf einen eigenen Rechner auslagern.

Mavarik 23. Feb 2019 11:05

AW: "Single-User" -> "Multi-User" + SQLite
 
Zitat:

Zitat von Ghostwalker (Beitrag 1426283)
Ich persönlich würde die Kommunikation und das DB Handling in ein eigenes Serverprogramm ohne GUI (Dienst/Daemon) auslagern. Das Serverprogramm nimmt die Daten der Clients entgegen, packt diese in eine Que. Ein eigener Thread des Serverprogramm arbeitet die Que ab und trägt diese in die DB ein.

Sicherlich ein guter Vorschlag!

Aber muss man nicht in jeder App, egal ob Windows, iOS oder Android, die Datenbankzugriffe kapseln?

Ich hatte noch nie ne App bei der ich nicht Daten in einem Thread weg schreibe oder Daten lese, während die UI auch Daten anfordert oder schreiben möchte?

Wenn ich also immer asynchron mit CRUD arbeite habe ich "keine" Probleme egal wie die Anwendung aus sieht.

Es gibt natürlich Situationen, wo die UI auf ein Ergebnis der Datenbank warten muss. Aber wovon sprechen wir hier? 250ms? 1s? 3s?

Wenn ich auf einen Button klicke, erwarte ich eine sofortige Reaktion. IMMER, damit sich die Anwendung flüssig "anfühlt". Wenn also ein Zugriff länger dauert, muss ich sowieso eine Art von Stundenglas/Wait-Animation anzeigen.
Naja und die kann sich auch nur flüssig drehen, wenn mein DB-Zugriff in einem eigenen Thread ist...

Also sind ALLE Datenbankzugriff immer in einem Thread. Hier also einen Queue einzufügen, die dann auch gerne Datenbankanfragen von mehrerer Quellen abhandeln kann ist kein Hexenwerk. Wenn ich dann noch anfragen der lokalen App bevorzuge, läuft alles schnell und sauber.

Wäre es nicht schön, wenn es für Firemonkey ein Framework gäbe, dass so etwas kann? :stupid:

Mavarik :coder:

Ghostwalker 24. Feb 2019 06:22

AW: "Single-User" -> "Multi-User" + SQLite
 
Naja, einfach ist es schon.

Die Frage nach der Priorisierung der Zugriffe, ist eine Frage, wie aktuell die Daten für die Clients sein müssen.

Beispiel:

Client A braucht unbedingt die Daten von Client B, die dieser gerade in die Que zum eintragen geschickt hat.

Dann sollte der Schreibzugriff natürlich oberste Prio haben.

Eine andere Situation, die man noch berücksichtigen könnte, wäre, das die Clients auch "Offline" arbeiten können sollen. Dann wärs sinnvoll die Clients mit einer eigenen "lokalen" DB arbeiten zu lassen, die dann entsprechend mit der zentralen Version synchronisiert werden.

p80286 24. Feb 2019 12:37

AW: "Single-User" -> "Multi-User" + SQLite
 
Angeblich sollen DBMS das von Hause aus können, aber ich kann mich auch irren.

Gruß
K-H

Frickler 24. Feb 2019 13:19

AW: "Single-User" -> "Multi-User" + SQLite
 
Schau Dir mal mORMot an, eventuell ist da ja eine Lösung. Und es basiert auf SQLite, auch für Multiuser-Zugriffe. Man kann aber auch andere Datenbanken verwenden.

Delphi.Narium 24. Feb 2019 13:42

AW: "Single-User" -> "Multi-User" + SQLite
 
Man schreibe sich ein Programm, das von allen Clients die Daten annimmt, bzw. ihnen die angeforderten Daten liefert.

Als Datenbank benutzte man ein DBMS, das auf der Plattform läuft, auf der dieses Programm laufen soll.

Dieses Programm dient nicht gleichzeitig als Client für irgendeinen Anwender.

Dabei ist es absolut irrelevant, ob das DBMS für alle Clientplattformen zur Verfügung steht oder nicht.

Man kann als DBMS auf 'nem Datenbankserver ruhig eine Datenbank nutzen, die nicht auf jedem Client läuft.

Das wäre ja fast so, als müsste Google für seine Suchmaschine einen Datenbank nutzen, die für jeden Client, von dem aus man die Googlesuche nutzt könnte, zur Verfügung steht.

Und wenn man für 'nen Client 'ne lokale Datenbank benötigt, dann nimmt man eine für den konkreten Client verfügbare Datenbank. D. h. aber nicht, dass man dann für alle Clients die gleiche Datenbank nutzen muss.

Auch eine Datensynchronisation zwischen Clients mit eigenen Datenbanken setzt nicht voraus, dass ein einheitliches DBMS genutzt wird.

Die Datenbankkomponenten, die Delphi so zur Verfügung stellt, sind alle ausreichend flexibel, um mit ihnen die unterschiedlichsten Datenbanken nutzen zu können. Und das können sie sogar so gut, dass es für die Implementierung der Software mit Delphi absolut irrelevant ist, welches DBMS nachher mit der Software angesprochen wird. Man muss halt ein bisserl Hirnschmalz beim Programmieren einsetzen und von den Datenbanken nicht ausschließlich die Feature nutzen, die sie als Alleinstellungsmerkmal haben. Mit dem SQL-Standard soll man da (angeblich) recht gut zurechtkommen ;-)


Alle Zeitangaben in WEZ +1. Es ist jetzt 03:41 Uhr.
Seite 2 von 2     12   

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz