I'm really having trouble understanding the fundamental purposes for Play's Iteratees and Enumerators.
I've read
I read this answer to find that instead of relying on a pulling model, like InputStream, it uses a pushing model.
Iteratees are an interesting beast -- on one hand, it "pushes" data to the handler, instead of relying to the handler to pull data, and, therefore, has better performance. On the other hand, it allows the handler to control when the flow should be stopped.
But then Play's documentation on Iteratees says
Or more generally enumerating a
java.io.InputStreamusingEnumerator.fromStream. It is important to note that input won’t be read until the iteratee this Enumerator is applied on is ready to take more input.
Wait....so what is going on?
Does the data get pushed by the Enumerator or pulled by the Iteratee? (i.e. who decides when it is time to calculate more data)
Both. It is entirely non-blocking for both ends of the stream.
The Enumerator doesn't push any data until the Iteratee is ready to receive it, and it doesn't push any more data until the Iteratee signals it is ready for more. At the same time, the Enumerator can take as long as it wants to push data. Neither process will block on the other.
This method, on Iteratee, is critical to understanding how it works:
abstract def fold[B](folder: (Step[E, A]) ⇒ Future[B])(implicit ec: ExecutionContext): Future[B]
This is the sole abstract method in Iteratee, the only one that must be implemented. All the rest of the methods are defined in terms of fold. When an Enumerator is applied to an Iteratee, it invokes this method, providing the folder which is effectively a callback. Once the Iteratee is ready, it invokes folder providing the state it is currently in, Cont if it can receive more data, Done if it doesn't need any more, or Error if something has gone wrong. And because folder returns a Future, it can take as long as it needs to provide further input if the Iteratee is in the Cont state.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With