Flutter 如何从firestore获取实时更新,同时保持构建方法的纯净?

Flutter 如何从firestore获取实时更新,同时保持构建方法的纯净?,flutter,stream,google-cloud-firestore,Flutter,Stream,Google Cloud Firestore,由此: 构建方法的设计应该是纯粹的/没有副作用的 及 这意味着构建方法不应触发http调用或修改任何状态 但这与用法示例相矛盾(为了简洁起见进行了精简): 前面提到的答案中的建议都不适用于这种情况。解决方案实际上是相同的:制作一个StatefulWidget class Foo extends StatefulWidget { @override _FooState createState() => _FooState(); } class _FooState extends S

由此:

构建方法的设计应该是纯粹的/没有副作用的

这意味着构建方法不应触发http调用或修改任何状态

但这与用法示例相矛盾(为了简洁起见进行了精简):


前面提到的答案中的建议都不适用于这种情况。

解决方案实际上是相同的:制作一个
StatefulWidget

class Foo extends StatefulWidget {
  @override
  _FooState createState() => _FooState();
}

class _FooState extends State<Foo> {
  Stream<QuerySnapshot> stream;

  @override
  void initState() {
    super.initState();
    stream = Firestore.instance.collection('books').snapshots();
  }

  @override
  Widget build(BuildContext context) {
    return StreamBuilder<QuerySnapshot>(
      stream: stream,
      builder: (BuildContext context, AsyncSnapshot<QuerySnapshot> snapshot) {
        //  do something with books
      },
    );
  }
}
class Foo扩展StatefulWidget{
@凌驾
_FooState createState()=>\u FooState();
}
类_FooState扩展了状态{
溪流;
@凌驾
void initState(){
super.initState();
stream=Firestore.instance.collection('books').snapshots();
}
@凌驾
小部件构建(构建上下文){
返回流生成器(
小溪:小溪,
生成器:(BuildContext上下文,异步快照){
//用书做点什么
},
);
}
}

解决方案实际上是一样的:制作一个
StatefulWidget

class Foo extends StatefulWidget {
  @override
  _FooState createState() => _FooState();
}

class _FooState extends State<Foo> {
  Stream<QuerySnapshot> stream;

  @override
  void initState() {
    super.initState();
    stream = Firestore.instance.collection('books').snapshots();
  }

  @override
  Widget build(BuildContext context) {
    return StreamBuilder<QuerySnapshot>(
      stream: stream,
      builder: (BuildContext context, AsyncSnapshot<QuerySnapshot> snapshot) {
        //  do something with books
      },
    );
  }
}
class Foo扩展StatefulWidget{
@凌驾
_FooState createState()=>\u FooState();
}
类_FooState扩展了状态{
溪流;
@凌驾
void initState(){
super.initState();
stream=Firestore.instance.collection('books').snapshots();
}
@凌驾
小部件构建(构建上下文){
返回流生成器(
小溪:小溪,
生成器:(BuildContext上下文,异步快照){
//用书做点什么
},
);
}
}

再次调用
builder
的事实与函数的纯度无关,这完全是错误的normal@R埃米·罗塞莱,但随后它将再次获取数据,这一次是不必要的,这很糟糕,不是吗?不,不会。再次调用生成器,但未提取数据again@Rémi Rousselet,这很酷,因此如果可以毫无问题地重复调用
builder
,那么使用
StatefulWidget
方法而不是普通的
无状态widget
?是的,因为使用
无状态widget
,例如打开键盘,将使您的构建方法创建一个新流。这可能会导致额外的firebase请求(尽管很难验证)。再次调用
builder
与函数的纯度无关,这完全是错误的normal@R埃米·罗塞莱,但随后它将再次获取数据,这一次是不必要的,这很糟糕,不是吗?不,不会。再次调用生成器,但未提取数据again@Rémi Rousselet,这很酷,因此如果可以毫无问题地重复调用
builder
,那么使用
StatefulWidget
方法而不是普通的
无状态widget
?是的,因为使用
无状态widget
,例如打开键盘,将使您的构建方法创建一个新流。这可能会导致额外的firebase请求(尽管很难验证)。感谢您的回答,但我在
build
builder
中添加了打印,不幸的是,它们都是在我换手机后随时打印的orientation@D31但是正如你链接的答案在帖子中所说的(顺便说一下,这是我的答案):这没关系
build
(因此,
builder
)可以随时调用。事实上,正是因为
builder
被频繁触发,所以它应该没有副作用。获取数据的实际工作发生在您的
属性中,它不会为每个
构建
触发。感谢您的回答,但我在
构建
构建
中添加了打印,不幸的是,它们都会在之后随时打印,例如,我换了电话orientation@D31但是正如你链接的答案在帖子中所说的(顺便说一下,这是我的答案):这没关系
build
(因此,
builder
)可以随时调用。事实上,正是因为
builder
被频繁触发,所以它应该没有副作用。获取数据的实际工作发生在
属性中,它不会在每次
构建
时触发。
class Foo extends StatefulWidget {
  @override
  _FooState createState() => _FooState();
}

class _FooState extends State<Foo> {
  Stream<QuerySnapshot> stream;

  @override
  void initState() {
    super.initState();
    stream = Firestore.instance.collection('books').snapshots();
  }

  @override
  Widget build(BuildContext context) {
    return StreamBuilder<QuerySnapshot>(
      stream: stream,
      builder: (BuildContext context, AsyncSnapshot<QuerySnapshot> snapshot) {
        //  do something with books
      },
    );
  }
}