Scala Play`Enumerators`:推或拉?

时间:2014-07-12 14:10:03

标签: scala playframework iterate

我真的无法理解Play的IterateeEnumerator的基本目的。

我读过

我读了这个answer,发现它不是依赖拉动模型,而是InputStream,而是使用推模型。

  

Iteratees是一个有趣的野兽 - 一方面,它“将”数据“推送”到处理程序,而不是依靠处理程序来提取数据,因此具有更好的性能。另一方面,它允许处理程序控制何时应该停止流程。

但是,然后Play的Iteratee s文档说

  

或更一般地使用java.io.InputStream枚举Enumerator.fromStream。重要的是要注意,在应用此枚举器的iteratee准备好接受更多输入之前,不会读取输入。

等等......所以发生了什么事?

数据是由Enumerator推送还是由Iteratee提取的? (即谁决定何时计算更多数据)

1 个答案:

答案 0 :(得分:3)

两者。它对于流的两端完全没有阻塞。

EnumeratorIteratee准备接收数据之前不会推送任何数据,并且它不会推送任何更多数据,直到Iteratee发出信号为止准备好了。与此同时,Enumerator只要想要推送数据就可以。这两个过程都不​​会阻止另一个过程。

此方法在Iteratee上对于了解其工作原理至关重要:

abstract def fold[B](folder: (Step[E, A]) ⇒ Future[B])(implicit ec: ExecutionContext): Future[B]

这是Iteratee中唯一必须实现的抽象方法。所有其他方法都是根据fold定义的。当Enumerator应用于Iteratee时,它会调用此方法,提供有效回调的folder。在Iteratee准备就绪后,它会调用folder提供其当前所处的状态,Cont是否可以接收更多数据,Done如果它不需要任何更多,或Error如果出现问题。由于folder会返回Future,因此只要Iteratee处于Cont状态,就需要提供更多输入。