Flutter: метод '[]' был вызван для null. StreamProvider

У меня есть StreamProvider для чтения из Firebase Firestore, который отлично работает, когда в документе есть данные, но если еще не создан документ / коллекция, я получаю сообщение об ошибке «Метод '[]' был вызван с нулевым значением». Это просто чтение числа из firestore, если есть ноль, я хочу установить по умолчанию 0.

Я пробовал использовать свойство "initialdata" SteamProvider, установив значение 0, но не уверен, правильно ли я его настроил. Я думаю, что свойство "catchError" StreamProvider может работать, но я не могу найти никаких примеров в Интернете.

См. Ниже StreamProvider, он находится под MultiProvider. Ниже находится класс PomosWeekly, он просто читает int.

StreamProvider<PomosWeekly>.value(
            stream: Global.pomosWeeklyRef.documentStream2,
            initialData: PomosWeekly.initialData()),
class PomosWeekly {
  int count;

  PomosWeekly({this.count});

  factory PomosWeekly.fromMap(Map data) {
    return PomosWeekly(
      count: data['week'] ??
          0,
    );
  }

  factory PomosWeekly.initialData() {
    return PomosWeekly(
      count: 0,
    );
  }
}

Поток работает нормально, если в этом месте есть документы / поля, но ошибки, если документ еще не был создан, я просто хочу вернуть 0, если есть ошибка. Ошибка: «Метод '[]' был вызван с нулевым значением».


person Chris    schedule 08.07.2019    source источник
comment
попробуйте data.containsKey('week') ? data['week'] : 0   -  person WiseTap    schedule 08.07.2019
comment
Похоже, data это null   -  person Rémi Rousselet    schedule 08.07.2019
comment
Пробовали data.containsKey ('week')? data ['week']: 0, не годится.   -  person Chris    schedule 09.07.2019


Ответы (1)


Я столкнулся с аналогичной проблемой, надеюсь, это может дать вам некоторое представление о том, как вы можете подойти к проблеме. Изначально мой код выглядел так:

Widget build(BuildContext context) {
    final docre = Provider.of<DocumentSnapshot>(context);
    String docStr = '';
    if(docre != null){
      docStr = docre.data['docid'];
    } else {
      docStr = 'noData';
    }

    return MyStreamWidget();
}

После этого я получал ту же ошибку, что и вы, я настраивал код снова и снова и делал следующее: 1. Поместил код в блок try catch, где я использую docre. 2. Изменен оператор return с if-else.

Вот измененный код:

Widget build(BuildContext context) {
    final user = Provider.of<User>(context);
    final docre = Provider.of<DocumentSnapshot>(context);
    String docStr = '';
    try{
      docStr = docre.data['docid'];
    }catch(e){
    }

    return docStr != '' ? MyStreamWidget() : Text('');
}

Надеюсь, это поможет.

person Sarvesh Bhatnagar    schedule 08.05.2020
comment
При этом используется обработка исключений для потока управления, что является плохой практикой не только потому, что усложняет код, но и неэффективно. - person madgen; 09.05.2020