Konzeptionelle Frage: Zentrale Datenbank und Client-App

Diese Seite verwendet Cookies. Durch die Nutzung unserer Seite erklären Sie sich damit einverstanden, dass wir Cookies setzen. Weitere Informationen

  • SteveJ schrieb:

    macmoonshine schrieb:

    Eine Aufgabe mit zwei oder mehr schreibenden Operationen lässt sich über Optimistic Locking jedenfalls nicht absichern.
    Nö, so was willst du ja auch nicht. Client 1 lockt eine Tabelle, schreibt einen Eintrag und verliert die Verbindung, während er die zweite Operation durchführen will Client 2 wartet jetzt auf das Timeout...

    RDBMS ist keine schlechte Technik, das will ich damit nicht sagen. Die meisten Anwendungen brauchen die Skalierbarkeit der NoSQL-Datenbanken ja auch nicht. Und sogar auf dem Server ist SQLite oft ausreichend:

    sqlite.org/whentouse.html

    Das Geschäftsmodell mit Objective-C eine PostgreSQL-Datenbank ansprechen zu wollen erschließt sich mir allerdings nicht so ganz...
    Davon gehe ich aus.#

    Vor allem nach der Idee, eine Datenbanktabelle zu locken …
    Es hat noch nie etwas gefunzt. To tear down the Wall would be a Werror!
    25.06.2016: [Swift] gehört zu meinen *Favorite Tags* auf SO. In welcher Bedeutung von "favorite"?
  • SteveJ schrieb:

    Es gibt ja durchaus eine Menge gute Lösungen ohne einen eigenen löcherigen Webservice zu schreiben, zum Beispiel
    einen ordentlichen WebService zu schreiben. +scnr+
    «Applejack» "Don't you use your fancy mathematics to muddle the issue!"

    Iä-86! Iä-64! Awavauatsh fthagn!

    kmr schrieb:

    Ach, Du bist auch so ein leichtgläubiger Zeitgenosse, der alles glaubt, was irgendwelche Typen vor sich hin brabbeln. :-P
  • SteveJ schrieb:

    matz schrieb:

    Hast du positive Erfahrungen mit CouchBase gemacht?
    Wollte ich mir schon länger mal anschauen
    Nö, ich würde aber auch nicht auf OS X selber hosten wollen. Wenn Du es Dir gerne machen lässt, könnte ich noch Parse, Firebase und CloudKit ins Gespräch werfen. Es gibt natürlich noch viel mehr, zum Beispiel Azure...
    Alle Lösungen die über einen "unmittelbaren Datenbankzugriff" arbeiten, funktionieren in etwa so gut wie iCloud: Bei einfachen Sachen irgendwie, ansonsten nur extrem schwer bis gar nicht. Ich nehme an, du hast noch nie selbst versucht, eine auf mehreren Geräten hochgradig parallel laufende App mit wichtigen Daten zu schreiben. Dann wüsstest du das nämlich (Best case).

    Das liegt daran, dass du im Prinzip alle Geräte locken müsstest, wenn ein Gerät eine Änderung durchführt. Mal abgesehen davon, dass das ziemlich schwierig ist, ist Locking über Daten in einer Datenbank und dann auch noch über mehrere Geräte ziemlich hirnamputiert. Eigentlich sind ja Transactions dafür erfunden worden, damit das nicht passiert.

    Es geht bloß genug Anwendungsfälle, bei denen eine einfach funktionierende Lösung reicht.

    Das hat übrigens auch schon Apple erkannt, weil sie Christian nämlich genau zu unserem Geschäftsmodell mit serverseitigem Code befragt haben. Die hatten nämlich auch schon die Idee. Ups.
    Es hat noch nie etwas gefunzt. To tear down the Wall would be a Werror!
    25.06.2016: [Swift] gehört zu meinen *Favorite Tags* auf SO. In welcher Bedeutung von "favorite"?

  • Schön!

    Marco Feltmann schrieb:

    SteveJ schrieb:

    Es gibt ja durchaus eine Menge gute Lösungen ohne einen eigenen löcherigen Webservice zu schreiben, zum Beispiel
    einen ordentlichen WebService zu schreiben. +scnr+

    ... wenn man das kann. Die Praxis zeigt, das dies vielen Leuten nicht gegeben ist, auch wenn sie glauben sie könnten.

    Amin Negm-Awad schrieb:


    Alle Lösungen die über einen "unmittelbaren Datenbankzugriff" arbeiten, funktionieren in etwa so gut wie iCloud: Bei einfachen Sachen irgendwie, ansonsten nur extrem schwer bis gar nicht.

    CloudKit ist ziemlich klasse und kostenlos, es gibt natürlich noch die üblichen Verdächtigen wie AWS, Heroku, Digital Ocean ...

    Amin Negm-Awad schrieb:


    Es geht bloß genug Anwendungsfälle, bei denen eine einfach funktionierende Lösung reicht.

    Das hat übrigens auch schon Apple erkannt, weil sie Christian nämlich genau zu unserem Geschäftsmodell mit serverseitigem Code befragt haben. Die hatten nämlich auch schon die Idee. Ups.

    Na, wenn ihr schon Consulting für Apple macht, habt ihr ihnen auch gleich gesagt, dass sie Swift einstellen sollen, weil es Mist ist? Und CloudKit einstampfen?

    Nichts gegen serverseitigen Code, bisher nimmt man halt die oben genannten, und viele sind gespannt auf Swift auf Linux, aus eben jenem Grund. Aber erklär mir doch noch mal den Vorteil der Objective-C/PostgreSQL-Kombination?
  • Nein, hat Christian nicht gesagt, wenngleich es ihm vielleicht unter den Fingern juckte.

    Ich könnte jetzt noch einmal ausführen, warum die von dir genannten Lösungen ein Problem haben. Du würdest es mutmaßlich wieder aus dem Zitat löschen. Also mache ich es nicht.

    Mit Swift geht das übrigens nur eklig, weil Swift keine Messages kennt.
    Es hat noch nie etwas gefunzt. To tear down the Wall would be a Werror!
    25.06.2016: [Swift] gehört zu meinen *Favorite Tags* auf SO. In welcher Bedeutung von "favorite"?
  • Amin Negm-Awad schrieb:

    Ich könnte jetzt noch einmal ausführen, warum die von dir genannten Lösungen ein Problem haben. Du würdest es mutmaßlich wieder aus dem Zitat löschen. Also mache ich es nicht.

    Amin Negm-Awad schrieb:


    Das liegt daran, dass du im Prinzip alle Geräte locken müsstest, wenn ein Gerät eine Änderung durchführt. Mal abgesehen davon, dass das ziemlich schwierig ist, ist Locking über Daten in einer Datenbank und dann auch noch über mehrere Geräte ziemlich hirnamputiert. Eigentlich sind ja Transactions dafür erfunden worden, damit das nicht passiert.

    Es geht bloß genug Anwendungsfälle, bei denen eine einfach funktionierende Lösung reicht.

    Bitte. Besser?

    Jetzt erkläre doch noch mal, warum ich bei Parse, Firebase, CloudKit und Azure “alle Geräte locken” müsste, und wie man überhaupt Geräte lockt.

    Amin Negm-Awad schrieb:


    Mit Swift geht das übrigens nur eklig, weil Swift keine Messages kennt.

    Was ist denn “das”? Oder fehlt hier wieder Kontext?
  • SteveJ schrieb:

    matz schrieb:

    Hast du positive Erfahrungen mit CouchBase gemacht?
    Nö, ich würde aber auch nicht auf OS X selber hosten wollen. Wenn Du es Dir gerne machen lässt, könnte ich noch Parse, Firebase und CloudKit ins Gespräch werfen. Es gibt natürlich noch viel mehr, zum Beispiel Azure...

    Marco Feltmann schrieb:

    SteveJ schrieb:

    Parse, Firebase, CloudKit und Azure
    realisieren ihren Kram ja auch nicht via CouchDB…
    Jetzt wo du es sagst... ;)
  • SteveJ schrieb:

    Amin Negm-Awad schrieb:

    Ich könnte jetzt noch einmal ausführen, warum die von dir genannten Lösungen ein Problem haben. Du würdest es mutmaßlich wieder aus dem Zitat löschen. Also mache ich es nicht.

    Amin Negm-Awad schrieb:

    Das liegt daran, dass du im Prinzip alle Geräte locken müsstest, wenn ein Gerät eine Änderung durchführt. Mal abgesehen davon, dass das ziemlich schwierig ist, ist Locking über Daten in einer Datenbank und dann auch noch über mehrere Geräte ziemlich hirnamputiert. Eigentlich sind ja Transactions dafür erfunden worden, damit das nicht passiert.

    Es geht bloß genug Anwendungsfälle, bei denen eine einfach funktionierende Lösung reicht.
    Bitte. Besser?

    Jetzt erkläre doch noch mal, warum ich bei Parse, Firebase, CloudKit und Azure “alle Geräte locken” müsste, und wie man überhaupt Geräte lockt.

    Amin Negm-Awad schrieb:

    Mit Swift geht das übrigens nur eklig, weil Swift keine Messages kennt.
    Was ist denn “das”? Oder fehlt hier wieder Kontext?
    Oben:

    Wenn du keinen Code auf einem Server ausführen kannst, dann musst du dich dezentral synchronisieren. Jede Operation auf jedem Gerät kann aber auf einem nicht aktuellen Zustand erfolgen. Wobei das "aktuell" relativ ist, denn jedes Gerät hat eine andere Vorstellung davon, was aktuell ist. Sie hat zudem sogar eine andere Vorstellung davon, auf welchem Zustand sich andere Geräte befinden, sogar dann, wenn diese Information ebenfalls geteilt wird. Das heißt, das jede Operation eine innere Konsistenz der lokalen Kopie der DB verletzen kann, wenn ein Synch kommt.

    Das ist bei einfachen Operationen noch hinzunehmen, etwa wenn auf einem Gerät ein Eintrag editiert wird, der auf einem anderen gerade gelöscht ist. "Gerade" ist hierbei nicht im Bezug auf eine Weltzeit zu verstehen, sondern auf den letzten Synchronitätsstand. Das kann Wochen bedeuten, wenn du etwa zwei Geräte mit in den Urlaub nimmst, von denen eines Synch hat, das andere nicht.

    Bei einfachen Sachen geht das noch, etwa wenn man sagt, dass ein Zeitstempel maßgeblich ist. Allerdings kann das bedeuten, dass dutzende Operationen auf einem Gerät verworfen werden, weil zufällig auf dem anderen Gerät der Eintrag, auf dem die Operationen vorgenommen wurden, gelöscht wurde. Jetzt kann man natürlich sagen: Selber schuld, hättest halt nicht löschen sollen oder dich daran erinnern. Das nenne ich dann mäßig funktionieren. So ist das etwa in Kalender. (Bei schnellen Operationen einfügen, ändern, löschen bei langsamen Netz etwa, tauchen bei mir immer wieder die gelöschten Termine wieder auf.)

    Wenn du aber komplexere Operationen hast, wie etwa Einträge aggregieren und löschen, geht das Ganze in diese Hose. Versuche etwa nur sicherzustellen, dass es von einem Entitätstypen immer mindestens eine Entität gibt. Viel Spaß dabei! Synch-Loops sind da noch das geringste Problem.

    Core Data mildert dieses Problem etwa dadurch, dass es Baseline von Zeit zu Zeit verschickt, die dann also neue Ausgangslage für alle Geräte dienen. Dies kann freilich wieder zu Inkonsistenten führen, wenn verschiedene Geräte nicht einmal dieselbe Baseline haben.

    Eine Strategie, die das einigermaßen berücksichtigt, ist sehr komplex und wird immer einen applikationsspezifischen Kern haben. Das Hauptproblem ist aber, dass die Strategie ihrerseits wieder dezentral läuft und daher wiederum potentiell nur Teile sieht – jedes Gerät verschiedene. Jedes Gerät versucht dann ein Puzzle für alle Geräte zusammenzusetzen und jedes Gerät hat dabei verschiedene Puzzleteile.

    Du kannst das Ganze recht einfach lösen, wenn du eine zentrale Instanz aka Server hast. Der weiß nämlich schon zumindest einmal, wer welchen Stand hat und welche Geräte es überhaupt gibt. Das vereinfacht die Sache um Größenordnungen.

    Core Data wird deshalb in der Cloud nie komplex funktionieren. CloudKit und die anderen lösen das, indem sie einfach gar nichts selbständig machen und das Problem dem App-Programmierer überlassen, der es im schlimmsten Falle einfach übersieht (oder eine Scheinlösung erdenkt), nicht wahr, SteveJ.

    Aber das weißt du ja sicher alles, weil du Erfahrungen in dem Bereich hast und meine Vorträge dazu geschaut hast.

    Eine weitere Möglichkeit das Problem zu lösen, ist vor jeder Operation ein Lock i die DB zu schreiben. (So geht das übrigens.) Das schließt dann nur Offline-Arbeiten aus und führt zu unerträglichen Wartezeiten.

    Zu unten:

    Ich erkläre dir gerne, was "das" ist, obwohl ich es hier schon getan habe:

    Das heißt das einfache Abbilden von HTTP-Nachrichten auf In-App-Nachrichten. In Objective-C kannst du einfach aus URLs, Bodies, $whatever was ein Text ist, eine Message zusammenbauen, die gleich richtig adressiert wird. In Swift fällt das schon deutlich schwerer.
    Es hat noch nie etwas gefunzt. To tear down the Wall would be a Werror!
    25.06.2016: [Swift] gehört zu meinen *Favorite Tags* auf SO. In welcher Bedeutung von "favorite"?
  • Amin Negm-Awad schrieb:

    Wenn du keinen Code auf einem Server ausführen kannst, dann musst du dich dezentral synchronisieren.

    Geht jetzt am aktuellen Anwendungsfall vorbei:

    mrtn.lxo schrieb:

    Ich möchte eine zentrale Datenbank auf einem Webserver erstellen, die ich
    1) mit einer Backend-App befüllen möchte und
    2) von der ich Daten abrufen möchte im Kontext einer Client-App (das ist letztlich das Produkt)

    Insofern passten meine Vorschläge schon. Aber nehmen wir an, du wolltest synchronisieren.

    Amin Negm-Awad schrieb:

    Jede Operation auf jedem Gerät kann aber auf einem nicht aktuellen Zustand erfolgen. Wobei das "aktuell" relativ ist, denn jedes Gerät hat eine andere Vorstellung davon, was aktuell ist.

    Genau, die Frage ist ob es eine Definition des “aktuellen” Zustand gibt.

    Amin Negm-Awad schrieb:

    Eine Strategie, die das einigermaßen berücksichtigt, ist sehr komplex und wird immer einen applikationsspezifischen Kern haben.

    Konfliktauflösung muss natürlich je nach Anwendungsfall spezifiziert werden, im Zweifelsfall manuell auf der Clientseite ;)

    Amin Negm-Awad schrieb:

    Du kannst das Ganze recht einfach lösen, wenn du eine zentrale Instanz aka Server hast. Der weiß nämlich schon zumindest einmal, wer welchen Stand hat und welche Geräte es überhaupt gibt.

    Wer welchen Stand hat weiß er natürlich nicht, weil er ja die Operationen die die Clients ausgeführt haben erst mal nicht kennt.

    Das die “zentrale Instanz”-Lösung oft nur so-la-la funktioniert schreibst du ja kurz vorher selber:

    Amin Negm-Awad schrieb:

    So ist das etwa in Kalender. (Bei schnellen Operationen einfügen, ändern, löschen bei langsamen Netz etwa, tauchen bei mir immer wieder die gelöschten Termine wieder auf.)

    Amin Negm-Awad schrieb:

    CloudKit und die anderen lösen das, indem sie einfach gar nichts selbständig machen

    Nö:

    iCloud Design Guide schrieb:

    When a device attached to an iCloud account tries to write a value to key-value storage, iCloud checks to see if any recent changes have been made to the key-value store by other devices. If no changes have been made recently, the NSUbiquitousKeyValueStore object writes the pending local changes to the server. If changes were made recently, it does not write the local values to the server. Instead, it generates a NSUbiquitousKeyValueStoreDidChangeExternallyNotification notification to force your app to update itself based on the updated server values.

    Alles eingebaut, Apple ist ja nicht blöd. Auch wenn du das vermutest...

    Amin Negm-Awad schrieb:

    Aber das weißt du ja sicher alles, weil du Erfahrungen in dem Bereich hast und meine Vorträge dazu geschaut hast.

    Ach so, DU bist die Quelle der Weisheit? Das wusste ich nicht :love:

    Amin Negm-Awad schrieb:

    Das heißt das einfache Abbilden von HTTP-Nachrichten auf In-App-Nachrichten. In Objective-C kannst du einfach aus URLs, Bodies, $whatever was ein Text ist, eine Message zusammenbauen, die gleich richtig adressiert wird. In Swift fällt das schon deutlich schwerer.

    Was sind HTTP-Nachrichten? Meinst Du ein Request-Response-Paar? Den Status Code?

    Oder bist du jetzt auf Serverseite und meinst du einen HTTP Request Router?
  • Ich glaube, du hast es noch nicht verstanden:

    1. Natürlich will er synchronisieren. Irgendeinen Grund muss es ja haben, dass er in ein BE schreibt. Wenn es nur um die Daten eines Gerätes ging, könnte man sich das ja sparen.

    2. Ich hatte geschrieben, dass der Server alle Stände und Geräte kennt. Zu jedem Zeitpunkt, zu dem er mit einem konfrontiert wird. Ihm noch nicht bekannte Stände sind offenkundig für ihn gleichgültig, weil er sich nur um die Konsistenz seiner Datenbank kümmern muss. Die kann man immer als maßgebend deklarieren. Das geht bei Konfliktlösungen auf der Clientseite nicht. Die muss für alle auflösen, sogar für diejenigen, die sie gar nicht kennt. Und es lässt sich nicht sagen, welches Gerät maßgeblich ist.

    Ich hatte ja eigentlich – du hast das ja mal wieder gelöscht – auch für dein Verständnis ein recht einfaches Beispiel der Default-Entität gegeben. Das geht serverseitig ganz einfach, clientseitig schwer.

    Außerdem hatte ich auch nicht gesagt, dass sich das servereseitig von alleine löst, sondern um Größenordnungen leichter.

    3. Nein, das was Cloudkit anbietet, hilft nicht. (Jedenfalls nicht vollständig.) Du bekommst ja nur mitgeteilt, dass sich ein Schlüssel zwischenzeitlich geändert hat. Du hast nicht einmal einen Blick auf das Gesamte. (Es sei denn, du holst es dir ab.) Versuche einmal das einfache Beispiel damit zu lösen. Du wirst selbst sehen, wie schwierig das ist. Dass ein anderer das in der Zwischenzeit ebenso gemacht hat, hilft da nicht. Das kannst du auch so erfahren. Nur: Was nun?

    4. Ich bin nicht die Quelle der Weisheit, aber was ich dir hier erklären muss, weiß jeder mit Erfahrung oder jeder, der in meinen Vorträgen dazu saß. Da du dieses Wissen nicht hast, gehe ich davon aus, dass beides auf dich nicht zutrifft.

    5. Ja, ich meinte, dass HTTP-Requests geroutet werden. Argumente dekodiert, …
    Es hat noch nie etwas gefunzt. To tear down the Wall would be a Werror!
    25.06.2016: [Swift] gehört zu meinen *Favorite Tags* auf SO. In welcher Bedeutung von "favorite"?
  • Also eigentlich drückt sich der Threadersteller ja sehr klar aus:
    Im Prinzip könnte er einfach vorgehen wie bei einer langweiligen, statischen Website, bei der man via FTP (oder mit was besserem) zentral Daten aufspielt, die dann von den Clients via HTTP(S) abgeholt werden; das ganze aber wahrscheinlich mit vielen kleinen Datenpaketen, die in einer DB besser aufgehoben sind.
    Die ganze Komplexität ist bisher nur herbeifantasiert.
  • Amin Negm-Awad schrieb:

    Ich hatte geschrieben, dass der Server alle Stände und Geräte kennt. Zu jedem Zeitpunkt, zu dem er mit einem konfrontiert wird. Ihm noch nicht bekannte Stände sind offenkundig für ihn gleichgültig, weil er sich nur um die Konsistenz seiner Datenbank kümmern muss.

    Das gilt für jeden “Client” genau so.

    Amin Negm-Awad schrieb:

    Die kann man immer als maßgebend deklarieren.

    Kann man, muss man nicht. Willkommen in der Welt der verteilten Datenbankanwendungen.

    Amin Negm-Awad schrieb:

    Das geht bei Konfliktlösungen auf der Clientseite nicht. Die muss für alle auflösen, sogar für diejenigen, die sie gar nicht kennt. Und es lässt sich nicht sagen, welches Gerät maßgeblich ist.

    Klappt ja bei Git auch. Ist halt der Unterschied zwischen verteilten und zentralisierten Systemen mit einem Single Point of Failure.

    Amin Negm-Awad schrieb:

    Ich hatte ja eigentlich – du hast das ja mal wieder gelöscht

    Wikipedia schrieb:

    Fullquotes werden in verschiedenen Bereichen netzbasierter Kommunikation als schlechter Zitatstil gewertet

    Ist schon klar, dass du dich so klasse findest, dass alles was du an goldenen Worten von dir gibst wiederholt werden muss. Ich glaube Leute können auch nicht viel weiter oben den kompletten Text lesen, wenn sie wollen. Ist ja auch noch mal im Namen über dem Zitat verlinkt...

    Amin Negm-Awad schrieb:

    Ja, ich meinte, dass HTTP-Requests geroutet werden. Argumente dekodiert, …

    Ah, dann. HTTP-Routing-Bibliotheken gibt es in den klassischen Serversprachen ja genügend, da stellt sich mir doch wieder die Frage der Sinnhaftigkeit von Objective-C auf dem Server. Gibt es irgendwas Open-Source von euch?
  • SteveJ schrieb:

    Das gilt für jeden “Client” genau so.
    Nein, offenkundig nicht. Denn ein Client kann eine Verbindung zum Server gehabt haben und seitdem ein anderer Client nicht. Wenn er dann eine Operation ausführt und das Ergebnis beim nächsten Kontakt zurück liefert, kann es bereits nicht mehr zu dem passen, was aufgrund des anderen, ihm damals noch unbekannten Client, passiert ist.

    SteveJ schrieb:

    Kann man, muss man nicht. Willkommen in der Welt der verteilten Datenbankanwendungen.
    Manchmal muss man es eben. Nicht machen, geht immer.

    Ich begrüße dich in der Welt der verteilten Datenbankanwendungen. Und schaue, es gibt verschiedene Grde der Unabhängigkeit mit zunehmenden Problemen. Wozu gleich noch?


    SteveJ schrieb:

    Klappt ja bei Git auch. Ist halt der Unterschied zwischen verteilten und zentralisierten Systemen mit einem Single Point of Failure.
    Echt? Git meldet nie umaufgelöste Konflikte? Dann muss mein Git wohl kaputt sein.

    SteveJ schrieb:

    Ist schon klar, dass du dich so klasse findest, dass alles was du an goldenen Worten von dir gibst wiederholt werden muss. Ich glaube Leute können auch nicht viel weiter oben den kompletten Text lesen, wenn sie wollen. Ist ja auch noch mal im Namen über dem Zitat verlinkt...
    Ich entnehme dem, dass du bei den gelöschten Stellen wenig zu widersprechen hattest.


    SteveJ schrieb:

    Ah, dann. HTTP-Routing-Bibliotheken gibt es in den klassischen Serversprachen ja genügend, da stellt sich mir doch wieder die Frage der Sinnhaftigkeit von Objective-C auf dem Server. Gibt es irgendwas Open-Source von euch?
    Klar, es gibt andere Programmiersprachen. Wozu sollte ich gleich eine zweite nehmen. Wieget das eigentlich mit Swift? Immerhin war das das Thema, nicht dritte und vierte Programmiersprachen.

    Bleibt daneben immer noch die erste Frage offen: Wie garantierst du bei reiner Client-Sychnronisation, dass von einem Entitätstypen mindestens eine Entität existiert? Ist doch alles so supi bei dir. (Und nicht gleich wieder löschen, wenn man mal sein Geschwurbel belegen muss.)
    Es hat noch nie etwas gefunzt. To tear down the Wall would be a Werror!
    25.06.2016: [Swift] gehört zu meinen *Favorite Tags* auf SO. In welcher Bedeutung von "favorite"?