Deprecated function: Return type of Drupal\Core\Database\StatementWrapper::getIterator() should either be compatible with IteratorAggregate::getIterator(): Traversable, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in include() (line 10 of /mnt/web521/d1/47/510241947/htdocs/thomaskaemmerling.de/core/lib/Drupal/Core/Database/StatementWrapper.php).
include('/mnt/web521/d1/47/510241947/htdocs/thomaskaemmerling.de/core/lib/Drupal/Core/Database/StatementWrapper.php') (Line: 444)
Composer\Autoload\includeFile('/mnt/web521/d1/47/510241947/htdocs/thomaskaemmerling.de/vendor/composer/../../core/lib/Drupal/Core/Database/StatementWrapper.php') (Line: 322)
Composer\Autoload\ClassLoader->loadClass('Drupal\Core\Database\StatementWrapper') (Line: 557)
Drupal\Core\Database\Connection->prepareStatement('SELECT "cid", "data", "created", "expire", "serialized", "tags", "checksum" FROM "n99r_cache_container" WHERE "cid" IN ( :cids__0 ) ORDER BY "cid"', Array) (Line: 822)
Drupal\Core\Database\Connection->query('SELECT [cid], [data], [created], [expire], [serialized], [tags], [checksum] FROM {cache_container} WHERE [cid] IN ( :cids__0 ) ORDER BY [cid]', Array, Array) (Line: 97)
Drupal\Core\Database\Driver\mysql\Connection->query('SELECT [cid], [data], [created], [expire], [serialized], [tags], [checksum] FROM {cache_container} WHERE [cid] IN ( :cids[] ) ORDER BY [cid]', Array) (Line: 113)
Drupal\Core\Cache\DatabaseBackend->getMultiple(Array, ) (Line: 92)
Drupal\Core\Cache\DatabaseBackend->get('service_container:prod:9.1.4::Linux:a:1:{i:0;s:82:"/mnt/web521/d1/47/510241947/htdocs/thomaskaemmerling.de/sites/default/services.yml";}') (Line: 547)
Drupal\Core\DrupalKernel->getCachedContainerDefinition() (Line: 892)
Drupal\Core\DrupalKernel->initializeContainer() (Line: 471)
Drupal\Core\DrupalKernel->boot() (Line: 705)
Drupal\Core\DrupalKernel->handle(Object) (Line: 19)
Vom Umgang mit Futures und Promisses in Dart (Flutter) und Konzept Lasy function excecution | Thomas Kämmerling

Vom Umgang mit Futures und Promisses in Dart (Flutter) und Konzept Lasy function excecution

Gespeichert von Thomas am Sa., 20.02.2021 - 13:01

In der Programmierung mit Dart wird man um den Umgang mit Futures und Promisses nicht drum herumkommen.

In Dart werden von asynchronen Funktionen sogenannte Futures zurückgegeben. Bei einem Future wird ein Funktionsresultat zurückgegeben, welches auf einen Wert referenziert, der erst in der Zukunft existiert.

Bei einem Promis handelt es sich um eine Funktion die auf einen Future ausgeführt wird sobald der Future einen Wert erhält.

Future<Database> database;
database = openDatabase(p.join(value, "sample.db"));
//Promis wenn Datenbank initialisiert ist
database.then((db) => {
//db enthält das initialisierte Datenbank Objekt
//Code der die Datenbank betrifft kann hier ausgeführt werden
})

Bei einer Flutter-App die ich Entwickle wird der Datenbank-Layer initialisiert und sobald der Startbildschirm angezeigt wird sollen Daten aus der Datenbank angezeigt werden. Die Initialisierung der Datenbank verläuft jedoch asynchron. Dadurch kann ich nicht sicher sein, dass die Datenbank initialisiert ist wenn die Flutter-Page geladen wird. Deshalb musste ein Konzept her bei dem das Formular so früh wie möglich initialisiert wird, jedoch frühestens, wenn die Initialisierung der Datenbank abgeschlossen ist.

Um das zu realisieren habe ich eine Funktion erstellt an den ich den Funktionszeiger übergebe, der für die Initialisierung des Formulars zuständig ist. In dieser Funktion wird geprüft, ob die Datenbank verfügbar ist ansonsten wird die Funktion in eine Liste gehängt. Diese Liste an Funktionen wird dann ausgeführt, sobald die Datenbank fertig initialisiert ist.

In den folgenden Codeausschnitten wird das Konzept verdeutlicht.

Code im Widget:

 

class _MyHomePageState extends State<MyHomePage> {
//Erzeugen des Databaselayers
Databaselayer dbl = new Databaselayer();
......
  void initState() {
    super.initState();
   //Beim Initialisieren Funktionen eintragen die nach dem Initialisieren der Datenbank ausgeführt werden sollen 
   WidgetsBinding.instance.addPostFrameCallback((_) {
      dbl.addToInitFunktions(_bohneCounter);
      dbl.addToInitFunktions(_bohnenDummyData);
    });
  }
.......
void _bohneCounter(Database db) {
    //hier kann mit der Datenbank gearbeitet werden
    //in Promis wird die Datenbank übergeben
      dbl.database.then((db) => db....
    
}

Code im Databaselayer:
 

class Databaselayer {
  Future<Database> database;
  List<Function> initFunktionList = new List<Function>();

  Databaselayer() {


    // Datenbank öffnen und zuweisen
    getDatabasesPath().then((value) => {
          print(p.join(value, "beans.db")),
          database = openDatabase(p.join(value, "beans.db")),
          ......
                    database.then((db) => {executeAfterDataBaseInit(db)}))
                  }
              })
        });
  }
...........
 void addToInitFunktions(Function func) {
    if (database == null) {
     //Wenn die Datenbank noch noch nicht vorhanden ist in intit einhängen
     initFunktionList.add(func);
    } else {
     //wenn die Datenbank vorhanden ist kann die Funktion direkt ausgeführt werden
      this.database.then((db) => func(db));
    }
    return;
  }
  
  void executeAfterDataBaseInit(db) {
    //Alle Initfunktionen ausführen die in der Init-Liste stehen
    initFunktionList.forEach((func) {
      func(db);
    });
    return;
  }