Created
December 10, 2013 07:15
-
-
Save banshee/7886842 to your computer and use it in GitHub Desktop.
Talk for Seattle Scala group
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package com.restphone | |
import scalaz._ | |
import Scalaz._ | |
import scala.concurrent.Future | |
import scala.concurrent.Future._ | |
import scala.concurrent.Await | |
import scala.concurrent.duration._ | |
object MonadEvidenceThatWillMakeSenseLater { | |
import scala.concurrent.ExecutionContext.Implicits.global | |
// To use EitherT with a scala.concurrent.Future, we need to | |
// provide evidence that scala.concurrent.Future is a scalaz.Monad | |
implicit val convertScalaFutureToScalazMonad = new Monad[Future] { | |
def point[A](a: => A): Future[A] = Future { a } | |
def bind[A, B](fa: Future[A])(f: A => Future[B]): Future[B] = fa.flatMap(f) | |
} | |
} | |
object SimplifyErrorHandlingWithEitherT extends App { | |
import scala.concurrent.ExecutionContext.Implicits.global | |
import MonadEvidenceThatWillMakeSenseLater._ | |
type ProgramError = String // You'll have real types; this just makes the sample easier to read | |
// Working with Future[ProgramError \/ String] isn't straightforward | |
def workWithFutureOfProgramErrorOrString(input: Future[ProgramError \/ String]) = for { | |
x <- input // x is ProgramError \/ String; not quite what we want | |
lengthOfString = ??? | |
} yield 42 | |
def workDirectlyWithString(inputs: Future[ProgramError \/ String]) = for { | |
x <- EitherT(inputs) // notice the type of x is string, so we don't have to look at future or the error | |
lengthOfString = x.length | |
} yield lengthOfString | |
def useEitherTToSimplify(input: Future[ProgramError \/ String]): EitherT[Future, ProgramError, Int] = for { | |
x <- EitherT(input) | |
lengthOfString = x.length | |
} yield lengthOfString | |
// Use operations like fold to get a count ignoring errors. | |
val result = useEitherTToSimplify(Future { "abc".right }).fold(_ => 0, identity) | |
result.onComplete { | |
x => println(s"result is: $x") | |
} | |
val result2 = useEitherTToSimplify(Future { "BOOM!".left }).fold(_ => 0, identity) | |
result2.onComplete { | |
x => println(s"result is: $x") | |
} | |
Thread.sleep(2000) | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment