Seth Ladd
Seth Ladd

Reputation: 120569

What is the best way to `yield` over a collection/list that only exists inside of a callback, in Dart?

I have a method (_all) that has a callback (_runInTxn) inside. The callback gets the list (rs) that I would like to yield over and return via _all's Stream. However, the callback isn't marked with async* (but the method is marked as async*).

What is the best way to yield over a collection/list that only exists inside of a callback?

Here is an example of what is correct and works:

  Stream<String> _all() async* {
    var sql = 'SELECT id,value FROM $storeName';
    SqlResultSet resultSet;

    await _runInTxn((txn) {
      txn.executeSql(sql, [], (txn, rs) {
        resultSet = rs;
      });
    });

    for (var i = 0; i < resultSet.rows.length; ++i) {
      var row = resultSet.rows.item(i);
      yield row['value'];
    }
  }

I'm curious if there's a better way to write this code, so I can avoid a null resultSet. I'd really love to have my yield statement inside of the executeSql statement. Can I do a "non-local yield" ?

Upvotes: 1

Views: 105

Answers (1)

G&#252;nter Z&#246;chbauer
G&#252;nter Z&#246;chbauer

Reputation: 657476

There was a similar discussion about using yield inside Future.forEach() and the answer was as far as I remember that this is not supported (couldn't find the discussion yet).

I guess it would be easier without async*

Stream<String> _all() {
  var sql = 'SELECT id,value FROM $storeName';
  var sc = new StreamController<String>();

  _runInTxn((txn) {
    txn.executeSql(sql, [], (txn, rs) {
      rs.rows.forEach((row) => sc.add(row['value']));
    });
  }).then((_) => sc.close());

  return sc.stream;
}

try at DartPad

Upvotes: 1

Related Questions