Reactive Streams and Play 3.0

James Roper

Meanwhile in Australia

Used by permission of Art Mail Press
https://flic.kr/p/eUrf6f
https://flic.kr/p/5wPuC
https://flic.kr/p/bUGMw9
What is HTTP?
POST /main/screen HTTP/1.1
Host: earth.com
User-Agent: CATS
Accept: base/all
Content-Type: application/bomb
Content-Length: 45

You have no chance to survive make your time.
HTTP/1.1 403 Forbidden
Server: Captain
Content-Type: application/ZIG
Content-Length: 18

For great justice.
trait EssentialAction extends
  Request => Future[Result]

case class Request(
  header: RequestHeader,
  body: Bytes
)
case class Result(
  header: ResponseHeader,
  body: Bytes
)
POST /wall HTTP/1.1
Host: bar.com
Content-Type: beer/bottle
Content-Length: 100000000000

999999999 bottles of beer on the wall,
999999999 bottles of beer,
Take one down, pass it around,
999999998 bottles of beer on the wall.
999999998 bottles of beer on the wall,
999999998 bottles of beer,
Take one down, pass it around,
999999997 bottles of beer on the wall.

999999997 bottles of beer on the wall,
999999997 bottles of beer,
Take one down, pass it around,
999999996 bottles of beer on the wall.

999999996 bottles of beer on the wall,
999999996 bottles of beer,
Take one down, pass it around,
999999995 bottles of beer on the wall.

999999995 bottles of beer on the wall,
999999995 bottles of beer,
Take one down, pass it around,
999999994 bottles of beer on the wall.

999999994 bottles of beer on the wall,
999999994 bottles of beer,
Take one down, pass it around,
999999993 bottles of beer on the wall.

999999993 bottles of beer on the wall,
999999993 bottles of beer,
Take one down, pass it around,
999999992 bottles of beer on the wall.

999999992 bottles of beer on the wall,
999999992 bottles of beer,
Take one down, pass it around,
999999991 bottles of beer on the wall.
999999991 bottles of beer on the wall,
999999991 bottles of beer,
Take one down, pass it around,
999999990 bottles of beer on the wall.

999999990 bottles of beer on the wall,
999999990 bottles of beer,
Take one down, pass it around,
999999989 bottles of beer on the wall.

999999989 bottles of beer on the wall,
999999989 bottles of beer,
Take one down, pass it around,
999999988 bottles of beer on the wall.

999999988 bottles of beer on the wall,
999999988 bottles of beer,
Take one down, pass it around,
999999987 bottles of beer on the wall.

999999987 bottles of beer on the wall,
999999987 bottles of beer,
Take one down, pass it around,
999999986 bottles of beer on the wall.

999999986 bottles of beer on the wall,
999999986 bottles of beer,
Take one down, pass it around,
999999985 bottles of beer on the wall.

999999985 bottles of beer on the wall,
999999985 bottles of beer,
Take one down, pass it around,
999999984 bottles of beer on the wall.

999999984 bottles of beer on the wall,
999999984 bottles of beer,
Take one down, pass it around,
999999983 bottles of beer on the wall.

999999983 bottles of beer on the wall,
999999983 bottles of beer,
Take one down, pass it around,
999999982 bottles of beer on the wall.

999999982 bottles of beer on the wall,
999999982 bottles of beer,
Take one down, pass it around,
999999981 bottles of beer on the wall.

999999981 bottles of beer on the wall,
999999981 bottles of beer,
Take one down, pass it around,
999999980 bottles of beer on the wall.

999999980 bottles of beer on the wall,
999999980 bottles of beer,
Take one down, pass it around,
999999979 bottles of beer on the wall.

999999979 bottles of beer on the wall,
999999979 bottles of beer,
Take one down, pass it around,
999999978 bottles of beer on the wall.

999999978 bottles of beer on the wall,
999999978 bottles of beer,
Take one down, pass it around,
999999977 bottles of beer on the wall.

999999977 bottles of beer on the wall,
999999977 bottles of beer,
Take one down, pass it around,
999999976 bottles of beer on the wall.

999999976 bottles of beer on the wall,
999999976 bottles of beer,
Take one down, pass it around,
999999975 bottles of beer on the wall.

999999975 bottles of beer on the wall,
999999975 bottles of beer,
Take one down, pass it around,
999999974 bottles of beer on the wall.

999999974 bottles of beer on the wall,
999999974 bottles of beer,
Take one down, pass it around,
999999973 bottles of beer on the wall.

999999973 bottles of beer on the wall,
999999973 bottles of beer,
Take one down, pass it around,
999999972 bottles of beer on the wall.

999999972 bottles of beer on the wall,
999999972 bottles of beer,
Take one down, pass it around,
999999971 bottles of beer on the wall.

999999971 bottles of beer on the wall,
999999971 bottles of beer,
Take one down, pass it around,
999999970 bottles of beer on the wall.

999999970 bottles of beer on the wall,
999999970 bottles of beer,
Take one down, pass it around,
999999969 bottles of beer on the wall.

999999969 bottles of beer on the wall,
999999969 bottles of beer,
Take one down, pass it around,
999999968 bottles of beer on the wall.

999999968 bottles of beer on the wall,
999999968 bottles of beer,
Take one down, pass it around,
999999967 bottles of beer on the wall.

999999967 bottles of beer on the wall,
999999967 bottles of beer,
Take one down, pass it around,
999999966 bottles of beer on the wall.

999999966 bottles of beer on the wall,
999999966 bottles of beer,
Take one down, pass it around,
999999965 bottles of beer on the wall.

999999965 bottles of beer on the wall,
999999965 bottles of beer,
Take one down, pass it around,
999999964 bottles of beer on the wall.

999999964 bottles of beer on the wall,
999999964 bottles of beer,
Take one down, pass it around,
999999963 bottles of beer on the wall.

999999963 bottles of beer on the wall,
999999963 bottles of beer,
Take one down, pass it around,
999999962 bottles of beer on the wall.

999999962 bottles of beer on the wall,
999999962 bottles of beer,
Take one down, pass it around,
999999961 bottles of beer on the wall.

999999961 bottles of beer on the wall,
999999961 bottles of beer,
Take one down, pass it around,
999999960 bottles of beer on the wall.

999999960 bottles of beer on the wall,
999999960 bottles of beer,
Take one down, pass it around,
999999959 bottles of beer on the wall.

999999959 bottles of beer on the wall,
999999959 bottles of beer,
Take one down, pass it around,
999999958 bottles of beer on the wall.

999999958 bottles of beer on the wall,
999999958 bottles of beer,
Take one down, pass it around,
999999957 bottles of beer on the wall.

999999957 bottles of beer on the wall,
999999957 bottles of beer,
Take one down, pass it around,
999999956 bottles of beer on the wall.

999999956 bottles of beer on the wall,
999999956 bottles of beer,
Take one down, pass it around,
999999955 bottles of beer on the wall.

999999955 bottles of beer on the wall,
999999955 bottles of beer,
Take one down, pass it around,
999999954 bottles of beer on the wall.

999999954 bottles of beer on the wall,
999999954 bottles of beer,
Take one down, pass it around,
999999953 bottles of beer on the wall.

999999953 bottles of beer on the wall,
999999953 bottles of beer,
Take one down, pass it around,
999999952 bottles of beer on the wall.

999999952 bottles of beer on the wall,
999999952 bottles of beer,
Take one down, pass it around,
999999951 bottles of beer on the wall.

999999951 bottles of beer on the wall,
999999951 bottles of beer,
Take one down, pass it around,
999999950 bottles of beer on the wall.

999999950 bottles of beer on the wall,
999999950 bottles of beer,
Take one down, pass it around,
999999949 bottles of beer on the wall.
POST /play/along HTTP/1.1
Host: lambchop.com
Content-Type: closing/credits
Transfer-Encoding: chunked

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because
B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

B4
This is the song that does not end,
it just goes on and on my friend,
some people started singing it not knowing what it was,
and they'll continue singing it forever just because

Iteratees

trait EssentialAction extends
  RequestHeader => Iteratee[Bytes, Response]

case class Response(
  header: ResponseHeader,
  body: Enumerator[Bytes]
)
def value = takeWhile(c => c != ',' && c != '\n').map(v => v.mkString.trim)

def values(state: Seq[String] = Seq()): Iteratee[Char, Seq[String]] = for {
  _        <- dropSpaces
  value    <- value
  _        <- dropSpaces
  nextChar <- takeOne
  values   <- nextChar match {
    case Some('\n') | None => Done[Char, Seq[String]](state :+ value)
    case Some(',')         => values(state :+ value)
    case Some(other)       => Error("Expected, LF or EOF", Input.El(other))
  }
} yield values

def csvLines = Enumeratee.grouped(values())
http://www.reactive-streams.org/
public interface Subscriber<T> {
    public void onSubscribe(Subscription s);
    public void onNext(T t);
    public void onError(Throwable t);
    public void onComplete();
}

Reactive Streams

public interface Subscription {
    public void request(int n);
    public void cancel();
}
Your search - HTTP response - did not match any documents.

Suggestions:

trait Accumulator[E, A] {
  def subscriber: Subscriber[E]
  def future: Future[A]

  ...
}
def map[B](
  f: A => B
): Accumulator[E, B]

def mapFuture[B](
  f: A => Future[B]
): Accumulator[E, B]

def recover(
  f: Throwable => A
): Accumulator[E, A]
...
def through[D](
  processor: Processor[D, E]
): Accumulator[D, A]
...
trait EssentialAction extends
  RequestHeader => Accumulator[Bytes, Response]
trait BodyParser[A] extends
  RequestHeader => Accumulator[Bytes, A]
  
object Action {
  def async[A](parser: BodyParser[A])(
    f: Request[A] => Future[Response]
  ) = EssentialAction { header =>

    parser(header).mapFuture { body => 
      f(Request(header, body))
    }

  }
}
object LoggingFilter extends EssentialFilter {
  def apply(next: EssentialAction) =

    EssentialAction { header =>

      val start = System.currentTimeMillis
      next(header).map { response =>
    
        val time = System.currentTimeMillis = start
        Logger.info(response.status + " response to "
          + header.path + " in  " + time + "ms")
        
        response 
      }
    }
}
implicit val system = ActorSystem("Sys")
val materializer = FlowMaterializer(MaterializerSettings())

val LoglevelPattern = """.*\[(DEBUG|INFO|WARN|ERROR)\].*""".r

// read lines from a log file
val source = Source.fromFile("src/main/resources/logfile.txt", "utf-8")
val completedFuture = Flow(source.getLines()).
  // group them by log level
  groupBy {
    case LoglevelPattern(level) => level
    case other                  => "OTHER"
  }.
  // write lines of each group to a separate file
  foreach {
    case (level, producer) =>
      val output = new PrintWriter(new FileOutputStream(s"target/log-$level.txt"), true)
      Flow(producer).
        foreach(line => output.println(line)).
        // close resource when the group stream is completed
        onComplete(materializer)(_ => Try(output.close()))
  }.
  onComplete(materializer) { _ =>
    Try(source.close())
    system.shutdown()
  }
What about iteratees?
What about Play 2.4?
What about Java?
public final Action index = action(request -> {
  return ok("Hello world");
});

public Action load(Long id) {
  return async(request -> {
    return Foos.load(id).map(foo ->
        ok(Json.toJson(foo)));
  });
}